@naturalcycles/js-lib 14.243.0 → 14.244.0

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.
@@ -15,6 +15,7 @@ export type LocalTimeInput = LocalTime | Date | IsoDateTimeString | UnixTimestam
15
15
  export type LocalTimeInputNullable = LocalTimeInput | null | undefined;
16
16
  export type LocalTimeFormatter = (ld: LocalTime) => string;
17
17
  export type DateTimeObject = DateObject & TimeObject;
18
+ export type DateTimeObjectInput = DateObject & Partial<TimeObject>;
18
19
  export interface DateObject {
19
20
  year: number;
20
21
  month: number;
@@ -32,12 +33,12 @@ export declare class LocalTime {
32
33
  * Returns [cloned] LocalTime that is based on the same unixtimestamp, but in UTC timezone.
33
34
  * Opposite of `.local()` method.
34
35
  */
35
- utc(): LocalTime;
36
+ toUTC(): LocalTime;
36
37
  /**
37
38
  * Returns [cloned] LocalTime that is based on the same unixtimestamp, but in local timezone.
38
39
  * Opposite of `.utc()` method.
39
40
  */
40
- local(): LocalTime;
41
+ toLocal(): LocalTime;
41
42
  /**
42
43
  * Returns [cloned] fake LocalTime that has yyyy-mm-dd hh:mm:ss in the provided timezone.
43
44
  * It is a fake LocalTime in a sense that it's timezone is not real.
@@ -85,25 +86,25 @@ export declare class LocalTime {
85
86
  getUTCOffsetString(tz: string): string;
86
87
  get(unit: LocalTimeUnit): number;
87
88
  set(unit: LocalTimeUnit, v: number, mutate?: boolean): LocalTime;
88
- year(): number;
89
- year(v: number): LocalTime;
90
- month(): number;
91
- month(v: number): LocalTime;
92
- week(): number;
93
- week(v: number): LocalTime;
94
- day(): number;
95
- day(v: number): LocalTime;
89
+ get year(): number;
90
+ setYear(v: number): LocalTime;
91
+ get month(): number;
92
+ setMonth(v: number): LocalTime;
93
+ get week(): number;
94
+ setWeek(v: number): LocalTime;
95
+ get day(): number;
96
+ setDay(v: number): LocalTime;
97
+ get hour(): number;
98
+ setHour(v: number): LocalTime;
99
+ get minute(): number;
100
+ setMinute(v: number): LocalTime;
101
+ get second(): number;
102
+ setSecond(v: number): LocalTime;
96
103
  /**
97
104
  * Based on ISO: 1-7 is Mon-Sun.
98
105
  */
99
- dayOfWeek(): ISODayOfWeek;
100
- dayOfWeek(v: ISODayOfWeek): LocalTime;
101
- hour(): number;
102
- hour(v: number): LocalTime;
103
- minute(): number;
104
- minute(v: number): LocalTime;
105
- second(): number;
106
- second(v: number): LocalTime;
106
+ get dayOfWeek(): ISODayOfWeek;
107
+ setDayOfWeek(v: ISODayOfWeek): LocalTime;
107
108
  setComponents(c: Partial<DateTimeObject>, mutate?: boolean): LocalTime;
108
109
  plusSeconds(num: number): LocalTime;
109
110
  plusMinutes(num: number): LocalTime;
@@ -129,7 +130,7 @@ export declare class LocalTime {
129
130
  * Returns how many days are in the current month.
130
131
  * E.g 31 for January.
131
132
  */
132
- daysInMonth(): number;
133
+ get daysInMonth(): number;
133
134
  isSame(d: LocalTimeInput): boolean;
134
135
  isBefore(d: LocalTimeInput, inclusive?: boolean): boolean;
135
136
  isSameOrBefore(d: LocalTimeInput): boolean;
@@ -176,15 +177,15 @@ export declare class LocalTime {
176
177
  * returns 0 if they are equal
177
178
  * returns -1 if this < d
178
179
  */
179
- cmp(d: LocalTimeInput): -1 | 0 | 1;
180
- getDateTimeObject(): DateTimeObject;
181
- getDateObject(): DateObject;
182
- getTimeObject(): TimeObject;
183
- fromNow(now?: LocalTimeInput): string;
184
- getDate(): Date;
180
+ compare(d: LocalTimeInput): -1 | 0 | 1;
181
+ toDateTimeObject(): DateTimeObject;
182
+ toDateObject(): DateObject;
183
+ toTimeObject(): TimeObject;
184
+ toFromNowString(now?: LocalTimeInput): string;
185
+ toDate(): Date;
185
186
  clone(): LocalTime;
186
- unix(): UnixTimestampNumber;
187
- unixMillis(): UnixTimestampMillisNumber;
187
+ get unix(): UnixTimestampNumber;
188
+ get unixMillis(): UnixTimestampMillisNumber;
188
189
  valueOf(): UnixTimestampNumber;
189
190
  toLocalDate(): LocalDate;
190
191
  /**
@@ -216,21 +217,26 @@ export declare class LocalTime {
216
217
  }
217
218
  declare class LocalTimeFactory {
218
219
  /**
219
- * Parses input String into LocalDate.
220
- * Input can already be a LocalDate - it is returned as-is in that case.
220
+ * Parses input String into LocalTime.
221
+ * Input can already be a LocalTime - it is returned as-is in that case.
221
222
  */
222
- of(d: LocalTimeInput): LocalTime;
223
+ from(input: LocalTimeInput): LocalTime;
224
+ fromDate(date: Date): LocalTime;
225
+ fromUnix(ts: UnixTimestampNumber): LocalTime;
223
226
  /**
224
227
  * Create LocalTime from unixTimestamp in milliseconds (not in seconds).
225
228
  */
226
- ofMillis(millis: UnixTimestampMillisNumber): LocalTime;
229
+ fromMillis(millis: UnixTimestampMillisNumber): LocalTime;
227
230
  /**
228
231
  * Returns null if invalid
229
232
  */
230
- parseOrNull(d: LocalTimeInputNullable): LocalTime | null;
231
- parseToDate(d: LocalTimeInput): Date;
232
- parseToUnixTimestamp(d: LocalTimeInput): UnixTimestampNumber;
233
- isValid(d: LocalTimeInputNullable): boolean;
233
+ fromOrNull(d: LocalTimeInputNullable): LocalTime | null;
234
+ fromStringOrNull(s: string | undefined | null): LocalTime | null;
235
+ fromDateTimeObject(input: DateTimeObjectInput): LocalTime;
236
+ private parseStringToDateOrNull;
237
+ isValid(input: LocalTimeInputNullable): boolean;
238
+ isValidString(isoString: string | undefined | null): boolean;
239
+ private assertNotNull;
234
240
  /**
235
241
  * Returns the IANA timezone e.g `Europe/Stockholm`.
236
242
  * https://en.wikipedia.org/wiki/List_of_tz_database_time_zones
@@ -250,15 +256,11 @@ declare class LocalTimeFactory {
250
256
  *
251
257
  * `localTime` function will instead return LocalTime of `now` for falsy input.
252
258
  */
253
- orUndefined(d: LocalTimeInputNullable): LocalTime | undefined;
259
+ orUndefined(input: LocalTimeInputNullable): LocalTime | undefined;
254
260
  /**
255
261
  * Creates a LocalTime from the input, unless it's falsy - then returns LocalTime.now
256
262
  */
257
- orNow(d: LocalTimeInputNullable): LocalTime;
258
- fromComponents(c: {
259
- year: number;
260
- month: number;
261
- } & Partial<DateTimeObject>): LocalTime;
263
+ orNow(input: LocalTimeInputNullable): LocalTime;
262
264
  sort(items: LocalTime[], dir?: SortDirection, mutate?: boolean): LocalTime[];
263
265
  minOrUndefined(items: LocalTimeInputNullable[]): LocalTime | undefined;
264
266
  min(items: LocalTimeInputNullable[]): LocalTime;
@@ -23,6 +23,10 @@ const SECONDS_IN_DAY = 86400;
23
23
  // const MILLISECONDS_IN_DAY = 86400000
24
24
  // const MILLISECONDS_IN_MINUTE = 60000
25
25
  const VALID_DAYS_OF_WEEK = new Set([1, 2, 3, 4, 5, 6, 7]);
26
+ // It supports 2 forms:
27
+ // 1. 2023-03-03
28
+ // 2. 2023-03-03T05:10:02
29
+ const DATE_TIME_REGEX = /^(\d{4})-(\d{2})-(\d{2})([T\s](\d{2}):(\d{2}):(\d{2}))?/;
26
30
  class LocalTime {
27
31
  constructor($date) {
28
32
  this.$date = $date;
@@ -31,14 +35,14 @@ class LocalTime {
31
35
  * Returns [cloned] LocalTime that is based on the same unixtimestamp, but in UTC timezone.
32
36
  * Opposite of `.local()` method.
33
37
  */
34
- utc() {
38
+ toUTC() {
35
39
  return new LocalTime(new Date(this.$date.toISOString()));
36
40
  }
37
41
  /**
38
42
  * Returns [cloned] LocalTime that is based on the same unixtimestamp, but in local timezone.
39
43
  * Opposite of `.utc()` method.
40
44
  */
41
- local() {
45
+ toLocal() {
42
46
  return new LocalTime(new Date(this.$date.getTime()));
43
47
  }
44
48
  /**
@@ -160,34 +164,58 @@ class LocalTime {
160
164
  }
161
165
  return t;
162
166
  }
163
- year(v) {
164
- return v === undefined ? this.get('year') : this.set('year', v);
167
+ get year() {
168
+ return this.$date.getFullYear();
165
169
  }
166
- month(v) {
167
- return v === undefined ? this.get('month') : this.set('month', v);
170
+ setYear(v) {
171
+ return this.set('year', v);
168
172
  }
169
- week(v) {
170
- return v === undefined ? getWeek(this.$date) : this.set('week', v);
173
+ get month() {
174
+ return this.$date.getMonth() + 1;
171
175
  }
172
- day(v) {
173
- return v === undefined ? this.get('day') : this.set('day', v);
176
+ setMonth(v) {
177
+ return this.set('month', v);
174
178
  }
175
- dayOfWeek(v) {
176
- const dow = (this.$date.getDay() || 7);
177
- if (v === undefined) {
178
- return dow;
179
- }
180
- (0, assert_1._assert)(VALID_DAYS_OF_WEEK.has(v), `Invalid dayOfWeek: ${v}`);
181
- return this.plus(v - dow, 'day');
179
+ get week() {
180
+ return getWeek(this.$date);
181
+ }
182
+ setWeek(v) {
183
+ return this.set('week', v);
184
+ }
185
+ get day() {
186
+ return this.$date.getDate();
182
187
  }
183
- hour(v) {
184
- return v === undefined ? this.get('hour') : this.set('hour', v);
188
+ setDay(v) {
189
+ return this.set('day', v);
185
190
  }
186
- minute(v) {
187
- return v === undefined ? this.get('minute') : this.set('minute', v);
191
+ get hour() {
192
+ return this.$date.getHours();
193
+ }
194
+ setHour(v) {
195
+ return this.set('hour', v);
196
+ }
197
+ get minute() {
198
+ return this.$date.getMinutes();
199
+ }
200
+ setMinute(v) {
201
+ return this.set('minute', v);
202
+ }
203
+ get second() {
204
+ return this.$date.getSeconds();
188
205
  }
189
- second(v) {
190
- return v === undefined ? this.get('second') : this.set('second', v);
206
+ setSecond(v) {
207
+ return this.set('second', v);
208
+ }
209
+ /**
210
+ * Based on ISO: 1-7 is Mon-Sun.
211
+ */
212
+ get dayOfWeek() {
213
+ return (this.$date.getDay() || 7);
214
+ }
215
+ setDayOfWeek(v) {
216
+ (0, assert_1._assert)(VALID_DAYS_OF_WEEK.has(v), `Invalid dayOfWeek: ${v}`);
217
+ const dow = this.$date.getDay() || 7;
218
+ return this.plus(v - dow, 'day');
191
219
  }
192
220
  setComponents(c, mutate = false) {
193
221
  const d = mutate ? this.$date : new Date(this.$date);
@@ -255,7 +283,7 @@ class LocalTime {
255
283
  }
256
284
  if (unit === 'year' || unit === 'month') {
257
285
  const d = addMonths(this.$date, unit === 'month' ? num : num * 12, mutate);
258
- return mutate ? this : exports.localTime.of(d);
286
+ return mutate ? this : exports.localTime.from(d);
259
287
  }
260
288
  return this.set(unit, this.get(unit) + num, mutate);
261
289
  }
@@ -266,7 +294,7 @@ class LocalTime {
266
294
  return Math.abs(this.diff(other, unit));
267
295
  }
268
296
  diff(other, unit) {
269
- const date2 = exports.localTime.parseToDate(other);
297
+ const date2 = exports.localTime.from(other).$date;
270
298
  const secDiff = (this.$date.valueOf() - date2.valueOf()) / 1000;
271
299
  if (!secDiff)
272
300
  return 0;
@@ -354,32 +382,32 @@ class LocalTime {
354
382
  * Returns how many days are in the current month.
355
383
  * E.g 31 for January.
356
384
  */
357
- daysInMonth() {
385
+ get daysInMonth() {
358
386
  return localDate_1.localDate.getMonthLength(this.$date.getFullYear(), this.$date.getMonth() + 1);
359
387
  }
360
388
  isSame(d) {
361
- return this.cmp(d) === 0;
389
+ return this.compare(d) === 0;
362
390
  }
363
391
  isBefore(d, inclusive = false) {
364
- const r = this.cmp(d);
392
+ const r = this.compare(d);
365
393
  return r === -1 || (r === 0 && inclusive);
366
394
  }
367
395
  isSameOrBefore(d) {
368
- return this.cmp(d) <= 0;
396
+ return this.compare(d) <= 0;
369
397
  }
370
398
  isAfter(d, inclusive = false) {
371
- const r = this.cmp(d);
399
+ const r = this.compare(d);
372
400
  return r === 1 || (r === 0 && inclusive);
373
401
  }
374
402
  isSameOrAfter(d) {
375
- return this.cmp(d) >= 0;
403
+ return this.compare(d) >= 0;
376
404
  }
377
405
  isBetween(min, max, incl = '[)') {
378
- let r = this.cmp(min);
406
+ let r = this.compare(min);
379
407
  // eslint-disable-next-line @typescript-eslint/prefer-string-starts-ends-with
380
408
  if (r < 0 || (r === 0 && incl[0] === '('))
381
409
  return false;
382
- r = this.cmp(max);
410
+ r = this.compare(max);
383
411
  if (r > 0 || (r === 0 && incl[1] === ')'))
384
412
  return false;
385
413
  return true;
@@ -394,13 +422,13 @@ class LocalTime {
394
422
  * Third argument allows to override "now".
395
423
  */
396
424
  isOlderThan(n, unit, now) {
397
- return this.isBefore(exports.localTime.of(now ?? new Date()).plus(-n, unit));
425
+ return this.isBefore(exports.localTime.from(now ?? new Date()).plus(-n, unit));
398
426
  }
399
427
  /**
400
428
  * Checks if this localTime is same or older (<=) than "now" by X units.
401
429
  */
402
430
  isSameOrOlderThan(n, unit, now) {
403
- return this.isSameOrBefore(exports.localTime.of(now ?? new Date()).plus(-n, unit));
431
+ return this.isSameOrBefore(exports.localTime.from(now ?? new Date()).plus(-n, unit));
404
432
  }
405
433
  /**
406
434
  * Checks if this localTime is younger (>) than "now" by X units.
@@ -412,13 +440,13 @@ class LocalTime {
412
440
  * Third argument allows to override "now".
413
441
  */
414
442
  isYoungerThan(n, unit, now) {
415
- return this.isAfter(exports.localTime.of(now ?? new Date()).plus(-n, unit));
443
+ return this.isAfter(exports.localTime.from(now ?? new Date()).plus(-n, unit));
416
444
  }
417
445
  /**
418
446
  * Checks if this localTime is same or younger (>=) than "now" by X units.
419
447
  */
420
448
  isSameOrYoungerThan(n, unit, now) {
421
- return this.isSameOrAfter(exports.localTime.of(now ?? new Date()).plus(-n, unit));
449
+ return this.isSameOrAfter(exports.localTime.from(now ?? new Date()).plus(-n, unit));
422
450
  }
423
451
  getAgeInYears(now) {
424
452
  return this.getAgeIn('year', now);
@@ -439,42 +467,42 @@ class LocalTime {
439
467
  return this.getAgeIn('second', now);
440
468
  }
441
469
  getAgeIn(unit, now) {
442
- return exports.localTime.of(now ?? new Date()).diff(this, unit);
470
+ return exports.localTime.from(now ?? new Date()).diff(this, unit);
443
471
  }
444
472
  /**
445
473
  * Returns 1 if this > d
446
474
  * returns 0 if they are equal
447
475
  * returns -1 if this < d
448
476
  */
449
- cmp(d) {
477
+ compare(d) {
450
478
  const t1 = this.$date.valueOf();
451
- const t2 = exports.localTime.parseToDate(d).valueOf();
479
+ const t2 = exports.localTime.from(d).$date.valueOf();
452
480
  if (t1 === t2)
453
481
  return 0;
454
482
  return t1 < t2 ? -1 : 1;
455
483
  }
456
- getDateTimeObject() {
484
+ toDateTimeObject() {
457
485
  return {
458
- ...this.getDateObject(),
459
- ...this.getTimeObject(),
486
+ ...this.toDateObject(),
487
+ ...this.toTimeObject(),
460
488
  };
461
489
  }
462
- getDateObject() {
490
+ toDateObject() {
463
491
  return {
464
492
  year: this.$date.getFullYear(),
465
493
  month: this.$date.getMonth() + 1,
466
494
  day: this.$date.getDate(),
467
495
  };
468
496
  }
469
- getTimeObject() {
497
+ toTimeObject() {
470
498
  return {
471
499
  hour: this.$date.getHours(),
472
500
  minute: this.$date.getMinutes(),
473
501
  second: this.$date.getSeconds(),
474
502
  };
475
503
  }
476
- fromNow(now = new Date()) {
477
- const msDiff = exports.localTime.parseToDate(now).valueOf() - this.$date.valueOf();
504
+ toFromNowString(now = new Date()) {
505
+ const msDiff = exports.localTime.from(now).$date.valueOf() - this.$date.valueOf();
478
506
  if (msDiff === 0)
479
507
  return 'now';
480
508
  if (msDiff >= 0) {
@@ -482,16 +510,16 @@ class LocalTime {
482
510
  }
483
511
  return `in ${(0, time_util_1._ms)(msDiff * -1)}`;
484
512
  }
485
- getDate() {
513
+ toDate() {
486
514
  return this.$date;
487
515
  }
488
516
  clone() {
489
517
  return new LocalTime(new Date(this.$date));
490
518
  }
491
- unix() {
519
+ get unix() {
492
520
  return Math.floor(this.$date.valueOf() / 1000);
493
521
  }
494
- unixMillis() {
522
+ get unixMillis() {
495
523
  return this.$date.valueOf();
496
524
  }
497
525
  valueOf() {
@@ -523,7 +551,7 @@ class LocalTime {
523
551
  * Returns e.g: `1984-06-21`, only the date part of DateTime
524
552
  */
525
553
  toISODate() {
526
- const { year, month, day } = this.getDateObject();
554
+ const { year, month, day } = this.toDateObject();
527
555
  return [
528
556
  String(year).padStart(4, '0'),
529
557
  String(month).padStart(2, '0'),
@@ -536,7 +564,7 @@ class LocalTime {
536
564
  * Returns e.g: `17:03:15` (or `17:03` with seconds=false)
537
565
  */
538
566
  toISOTime(seconds = true) {
539
- const { hour, minute, second } = this.getTimeObject();
567
+ const { hour, minute, second } = this.toTimeObject();
540
568
  return [
541
569
  String(hour).padStart(2, '0'),
542
570
  String(minute).padStart(2, '0'),
@@ -551,7 +579,7 @@ class LocalTime {
551
579
  * Returns e.g: `19840621_1705`
552
580
  */
553
581
  toStringCompact(seconds = false) {
554
- const { year, month, day, hour, minute, second } = this.getDateTimeObject();
582
+ const { year, month, day, hour, minute, second } = this.toDateTimeObject();
555
583
  return [
556
584
  String(year).padStart(4, '0'),
557
585
  String(month).padStart(2, '0'),
@@ -566,7 +594,7 @@ class LocalTime {
566
594
  return this.toISODateTime();
567
595
  }
568
596
  toJSON() {
569
- return this.unix();
597
+ return this.unix;
570
598
  }
571
599
  toMonthId() {
572
600
  return this.toISODate().slice(0, 7);
@@ -581,82 +609,117 @@ class LocalTime {
581
609
  exports.LocalTime = LocalTime;
582
610
  class LocalTimeFactory {
583
611
  /**
584
- * Parses input String into LocalDate.
585
- * Input can already be a LocalDate - it is returned as-is in that case.
612
+ * Parses input String into LocalTime.
613
+ * Input can already be a LocalTime - it is returned as-is in that case.
586
614
  */
587
- of(d) {
588
- const t = this.parseOrNull(d);
589
- (0, assert_1._assert)(t !== null, `Cannot parse "${d}" into LocalTime`, {
590
- input: d,
591
- });
592
- return t;
615
+ from(input) {
616
+ const lt = this.fromOrNull(input);
617
+ this.assertNotNull(lt, input);
618
+ return lt;
619
+ }
620
+ fromDate(date) {
621
+ return new LocalTime(date);
622
+ }
623
+ fromUnix(ts) {
624
+ return new LocalTime(new Date(ts * 1000));
593
625
  }
594
626
  /**
595
627
  * Create LocalTime from unixTimestamp in milliseconds (not in seconds).
596
628
  */
597
- ofMillis(millis) {
598
- return this.of(new Date(millis));
629
+ fromMillis(millis) {
630
+ return new LocalTime(new Date(millis));
599
631
  }
600
632
  /**
601
633
  * Returns null if invalid
602
634
  */
603
- parseOrNull(d) {
635
+ fromOrNull(d) {
604
636
  if (d instanceof LocalTime)
605
637
  return d;
606
- let date;
607
638
  if (d instanceof Date) {
608
- date = d;
639
+ return new LocalTime(d);
609
640
  }
610
- else if (typeof d === 'number') {
611
- date = new Date(d * 1000);
641
+ if (typeof d === 'number') {
642
+ return new LocalTime(new Date(d * 1000));
612
643
  }
613
- else if (!d) {
614
- // This check is after checking the number, to support `0`
615
- return null;
644
+ if (typeof d === 'string') {
645
+ return this.fromStringOrNull(d);
616
646
  }
617
- else if (typeof d !== 'string') {
618
- // unexpected type, e.g Function or something
647
+ // This check is after checking the number, to support `0`
648
+ // unexpected type, e.g Function or something
649
+ return null;
650
+ }
651
+ fromStringOrNull(s) {
652
+ const date = this.parseStringToDateOrNull(s);
653
+ return date ? new LocalTime(date) : null;
654
+ }
655
+ fromDateTimeObject(input) {
656
+ const { year, month, day = 1, hour = 0, minute = 0, second = 0 } = input;
657
+ return new LocalTime(new Date(year, month - 1, day, hour, minute, second));
658
+ }
659
+ parseStringToDateOrNull(s) {
660
+ if (!s)
661
+ return null;
662
+ // Slicing removes the "timezone component", and makes the date "local"
663
+ // e.g 2022-04-06T23:15:00+09:00
664
+ // becomes 2022-04-06T23:15:00
665
+ // date = new Date(d.slice(0, 19))
666
+ // Parsing is inspired by how Day.js does it
667
+ // Specifically, it ensures that `localTime('2023-03-03')` returns the expected Date, and not a day before
668
+ // Because `new Date('2023-03-03')` in NewYork gives you '2023-03-02 19:00:00 GMT-0500'
669
+ const m = s.match(DATE_TIME_REGEX);
670
+ // Validate in 3 ways:
671
+ // 1. Should match Regex.
672
+ // In some ways it's stricter than Date constructor, e.g it doesn't allow 2023/05/05
673
+ // In other ways it's looser, e.g it allows `2023-05-05T`, while Date constructor doesn't.
674
+ // 2. Date constructor (of Node/v8 implementation, which we know is different from e.g WebKit/Safari)
675
+ // should not return `Invalid Date`.
676
+ // 3. Year, month and day should be valid, e.g 2023-01-32 should not be allowed.
677
+ // UPD: Actually, 3 can be skipped, because 2 is catching it already
678
+ // UPD: 2 is skipped, 1 and 3 are kept
679
+ // if (!m || isNaN(new Date(s).getDate())) return null
680
+ if (!m)
681
+ return null;
682
+ const year = Number(m[1]);
683
+ const month = Number(m[2]);
684
+ const day = Number(m[3]);
685
+ const hour = Number(m[5]);
686
+ const minute = Number(m[6]);
687
+ const second = Number(m[7]);
688
+ // Validation for just the Date part
689
+ if (!year ||
690
+ !month ||
691
+ month < 1 ||
692
+ month > 12 ||
693
+ !day ||
694
+ day < 1 ||
695
+ day > localDate_1.localDate.getMonthLength(year, month)) {
619
696
  return null;
620
697
  }
621
- else {
622
- // Slicing removes the "timezone component", and makes the date "local"
623
- // e.g 2022-04-06T23:15:00+09:00
624
- // becomes 2022-04-06T23:15:00
625
- date = new Date(d.slice(0, 19));
626
- // We used to slice to remove the timezone information, now we don't
627
- // date = new Date(d)
628
- }
629
- // validation
630
- if (isNaN(date.getDate())) {
631
- // throw new TypeError(`Cannot parse "${d}" into LocalTime`)
698
+ // Validation for Date+Time string, since the string is longer than YYYY-MM-DD
699
+ if (s.length > 10 &&
700
+ (isNaN(hour) ||
701
+ isNaN(minute) ||
702
+ isNaN(second) ||
703
+ hour < 0 ||
704
+ hour > 23 ||
705
+ minute < 0 ||
706
+ minute > 59 ||
707
+ second < 0 ||
708
+ second > 59)) {
632
709
  return null;
633
710
  }
634
- return new LocalTime(date);
711
+ return new Date(year, month - 1, day, hour || 0, minute || 0, second || 0, 0);
635
712
  }
636
- parseToDate(d) {
637
- if (d instanceof LocalTime)
638
- return d.$date;
639
- if (d instanceof Date)
640
- return d;
641
- const date = typeof d === 'number' ? new Date(d * 1000) : new Date(d);
642
- (0, assert_1._assert)(!isNaN(date.getDate()), `Cannot parse "${d}" to Date`, {
643
- input: d,
644
- });
645
- return date;
713
+ isValid(input) {
714
+ return this.fromOrNull(input) !== null;
646
715
  }
647
- parseToUnixTimestamp(d) {
648
- if (typeof d === 'number')
649
- return d;
650
- if (d instanceof LocalTime)
651
- return d.unix();
652
- const date = d instanceof Date ? d : new Date(d);
653
- (0, assert_1._assert)(!isNaN(date.getDate()), `Cannot parse "${d}" to UnixTimestamp`, {
654
- input: d,
655
- });
656
- return date.valueOf() / 1000;
716
+ isValidString(isoString) {
717
+ return this.fromStringOrNull(isoString) !== null;
657
718
  }
658
- isValid(d) {
659
- return this.parseOrNull(d) !== null;
719
+ assertNotNull(lt, input) {
720
+ (0, assert_1._assert)(lt !== null, `Cannot parse "${input}" into LocalTime`, {
721
+ input,
722
+ });
660
723
  }
661
724
  /**
662
725
  * Returns the IANA timezone e.g `Europe/Stockholm`.
@@ -683,17 +746,14 @@ class LocalTimeFactory {
683
746
  *
684
747
  * `localTime` function will instead return LocalTime of `now` for falsy input.
685
748
  */
686
- orUndefined(d) {
687
- return d ? this.of(d) : undefined;
749
+ orUndefined(input) {
750
+ return input || input === 0 ? this.from(input) : undefined;
688
751
  }
689
752
  /**
690
753
  * Creates a LocalTime from the input, unless it's falsy - then returns LocalTime.now
691
754
  */
692
- orNow(d) {
693
- return d ? this.of(d) : this.now();
694
- }
695
- fromComponents(c) {
696
- return new LocalTime(new Date(c.year, c.month - 1, c.day || 1, c.hour || 0, c.minute || 0, c.second || 0));
755
+ orNow(input) {
756
+ return input || input === 0 ? this.from(input) : this.now();
697
757
  }
698
758
  sort(items, dir = 'asc', mutate = false) {
699
759
  const mod = dir === 'desc' ? -1 : 1;
@@ -712,7 +772,7 @@ class LocalTimeFactory {
712
772
  const items2 = items.filter(is_util_1._isTruthy);
713
773
  (0, assert_1._assert)(items2.length, 'localTime.min called on empty array');
714
774
  return items2
715
- .map(i => this.of(i))
775
+ .map(i => this.from(i))
716
776
  .reduce((min, item) => (min.$date.valueOf() <= item.$date.valueOf() ? min : item));
717
777
  }
718
778
  maxOrUndefined(items) {
@@ -722,7 +782,7 @@ class LocalTimeFactory {
722
782
  const items2 = items.filter(is_util_1._isTruthy);
723
783
  (0, assert_1._assert)(items2.length, 'localTime.max called on empty array');
724
784
  return items2
725
- .map(i => this.of(i))
785
+ .map(i => this.from(i))
726
786
  .reduce((max, item) => (max.$date.valueOf() >= item.$date.valueOf() ? max : item));
727
787
  }
728
788
  }
@@ -815,7 +875,7 @@ function differenceInMonths(a, b) {
815
875
  return -(wholeMonthDiff + ((b.getTime() - anchor) / (anchor2 - anchor)) * sign);
816
876
  }
817
877
  const localTimeFactory = new LocalTimeFactory();
818
- exports.localTime = localTimeFactory.of.bind(localTimeFactory);
878
+ exports.localTime = localTimeFactory.from.bind(localTimeFactory);
819
879
  // The line below is the blackest of black magic I have ever written in 2024.
820
880
  // And probably 2023 as well.
821
881
  Object.setPrototypeOf(exports.localTime, localTimeFactory);