@naturalcycles/js-lib 14.91.2 → 14.92.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.
@@ -19,12 +19,14 @@ export declare class LocalDate {
19
19
  static of(d: LocalDateConfig): LocalDate;
20
20
  static parseCompact(d: string): LocalDate;
21
21
  static fromDate(d: Date): LocalDate;
22
+ static fromDateUTC(d: Date): LocalDate;
22
23
  /**
23
24
  * Returns null if invalid.
24
25
  */
25
26
  static parseOrNull(d: LocalDateConfig): LocalDate | null;
26
27
  static isValid(iso: string): boolean;
27
28
  static today(): LocalDate;
29
+ static todayUTC(): LocalDate;
28
30
  static sort(items: LocalDate[], mutate?: boolean, descending?: boolean): LocalDate[];
29
31
  static earliestOrUndefined(items: LocalDate[]): LocalDate | undefined;
30
32
  static earliest(items: LocalDate[]): LocalDate;
@@ -39,6 +39,9 @@ class LocalDate {
39
39
  static fromDate(d) {
40
40
  return new LocalDate(d.getFullYear(), d.getMonth() + 1, d.getDate());
41
41
  }
42
+ static fromDateUTC(d) {
43
+ return new LocalDate(d.getUTCFullYear(), d.getUTCMonth() + 1, d.getUTCDate());
44
+ }
42
45
  /**
43
46
  * Returns null if invalid.
44
47
  */
@@ -64,6 +67,9 @@ class LocalDate {
64
67
  static today() {
65
68
  return this.fromDate(new Date());
66
69
  }
70
+ static todayUTC() {
71
+ return this.fromDateUTC(new Date());
72
+ }
67
73
  static sort(items, mutate = false, descending = false) {
68
74
  const mod = descending ? -1 : 1;
69
75
  return (mutate ? items : [...items]).sort((a, b) => a.cmp(b) * mod);
@@ -15,18 +15,20 @@ export interface LocalTimeComponents {
15
15
  */
16
16
  export declare class LocalTime {
17
17
  private $date;
18
+ utcMode: boolean;
18
19
  private constructor();
19
20
  /**
20
21
  * Parses input String into LocalDate.
21
22
  * Input can already be a LocalDate - it is returned as-is in that case.
22
23
  */
23
24
  static of(d: LocalTimeConfig): LocalTime;
25
+ utc(): this;
26
+ local(): this;
24
27
  /**
25
28
  * Returns null if invalid
26
29
  */
27
30
  static parseOrNull(d: LocalTimeConfig): LocalTime | null;
28
31
  static isValid(d: LocalTimeConfig): boolean;
29
- static unix(ts: UnixTimestamp): LocalTime;
30
32
  static now(): LocalTime;
31
33
  static fromComponents(c: {
32
34
  year: number;
@@ -69,6 +71,7 @@ export declare class LocalTime {
69
71
  */
70
72
  cmp(d: LocalTimeConfig): -1 | 0 | 1;
71
73
  components(): LocalTimeComponents;
74
+ fromNow(now?: LocalTimeConfig): string;
72
75
  getDate(): Date;
73
76
  clone(): LocalTime;
74
77
  unix(): UnixTimestamp;
@@ -84,6 +87,10 @@ export declare class LocalTime {
84
87
  * Returns e.g: `1984-06-21`, only the date part of DateTime
85
88
  */
86
89
  toISODate(): IsoDate;
90
+ /**
91
+ * Returns e.g: `17:03:15` (or `17:03` with seconds=false)
92
+ */
93
+ toISOTime(seconds?: boolean): string;
87
94
  /**
88
95
  * Returns e.g: `19840621_1705`
89
96
  */
@@ -2,6 +2,7 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.localTime = exports.LocalTime = void 0;
4
4
  const assert_1 = require("../error/assert");
5
+ const time_util_1 = require("../time/time.util");
5
6
  const localDate_1 = require("./localDate");
6
7
  /* eslint-disable no-dupe-class-members */
7
8
  // Design choices:
@@ -17,8 +18,9 @@ const localDate_1 = require("./localDate");
17
18
  * @experimental
18
19
  */
19
20
  class LocalTime {
20
- constructor($date) {
21
+ constructor($date, utcMode) {
21
22
  this.$date = $date;
23
+ this.utcMode = utcMode;
22
24
  }
23
25
  /**
24
26
  * Parses input String into LocalDate.
@@ -31,6 +33,14 @@ class LocalTime {
31
33
  }
32
34
  return t;
33
35
  }
36
+ utc() {
37
+ this.utcMode = true;
38
+ return this;
39
+ }
40
+ local() {
41
+ this.utcMode = false;
42
+ return this;
43
+ }
34
44
  /**
35
45
  * Returns null if invalid
36
46
  */
@@ -52,106 +62,110 @@ class LocalTime {
52
62
  // throw new TypeError(`Cannot parse "${d}" into LocalTime`)
53
63
  return null;
54
64
  }
55
- return new LocalTime(date);
65
+ // if (utc) {
66
+ // date.setMinutes(date.getMinutes() + date.getTimezoneOffset())
67
+ // }
68
+ return new LocalTime(date, false);
56
69
  }
57
70
  static isValid(d) {
58
71
  return this.parseOrNull(d) !== null;
59
72
  }
60
- static unix(ts) {
61
- return new LocalTime(new Date(ts * 1000));
62
- }
63
73
  static now() {
64
- return this.of(new Date());
74
+ return new LocalTime(new Date(), false);
65
75
  }
66
76
  static fromComponents(c) {
67
- return new LocalTime(new Date(c.year, c.month - 1, c.day, c.hour, c.minute, c.second));
77
+ return new LocalTime(new Date(c.year, c.month - 1, c.day, c.hour, c.minute, c.second), false);
68
78
  }
69
79
  get(unit) {
70
80
  if (unit === 'year') {
71
- return this.$date.getFullYear();
81
+ return this.utcMode ? this.$date.getUTCFullYear() : this.$date.getFullYear();
72
82
  }
73
83
  if (unit === 'month') {
74
- return this.$date.getMonth() + 1;
84
+ return (this.utcMode ? this.$date.getUTCMonth() : this.$date.getMonth()) + 1;
75
85
  }
76
86
  if (unit === 'day') {
77
- return this.$date.getDate();
87
+ return this.utcMode ? this.$date.getUTCDate() : this.$date.getDate();
78
88
  }
79
89
  if (unit === 'hour') {
80
- return this.$date.getHours();
90
+ return this.utcMode ? this.$date.getUTCHours() : this.$date.getHours();
81
91
  }
82
92
  if (unit === 'minute') {
83
- return this.$date.getMinutes();
93
+ return this.utcMode ? this.$date.getUTCMinutes() : this.$date.getMinutes();
84
94
  }
85
95
  // second
86
- return this.$date.getSeconds();
96
+ return this.utcMode ? this.$date.getUTCSeconds() : this.$date.getSeconds();
87
97
  }
88
98
  set(unit, v, mutate = false) {
89
99
  const t = mutate ? this : this.clone();
100
+ /* eslint-disable @typescript-eslint/no-unused-expressions */
90
101
  if (unit === 'year') {
91
- t.$date.setFullYear(v);
102
+ this.utcMode ? t.$date.setUTCFullYear(v) : t.$date.setFullYear(v);
92
103
  }
93
104
  else if (unit === 'month') {
94
- t.$date.setMonth(v - 1);
105
+ this.utcMode ? t.$date.setUTCMonth(v - 1) : t.$date.setMonth(v - 1);
95
106
  }
96
107
  else if (unit === 'day') {
97
- t.$date.setDate(v);
108
+ this.utcMode ? t.$date.setUTCDate(v) : t.$date.setDate(v);
98
109
  }
99
110
  else if (unit === 'hour') {
100
- t.$date.setHours(v);
111
+ this.utcMode ? t.$date.setUTCHours(v) : t.$date.setHours(v);
101
112
  }
102
113
  else if (unit === 'minute') {
103
- t.$date.setMinutes(v);
114
+ this.utcMode ? t.$date.setUTCMinutes(v) : t.$date.setMinutes(v);
104
115
  }
105
116
  else if (unit === 'second') {
106
- t.$date.setSeconds(v);
117
+ this.utcMode ? t.$date.setUTCSeconds(v) : t.$date.setSeconds(v);
107
118
  }
119
+ /* eslint-enable @typescript-eslint/no-unused-expressions */
108
120
  return t;
109
121
  }
110
122
  year(v) {
111
- return v === undefined ? this.$date.getFullYear() : this.set('year', v);
123
+ return v === undefined ? this.get('year') : this.set('year', v);
112
124
  }
113
125
  month(v) {
114
- return v === undefined ? this.$date.getMonth() + 1 : this.set('month', v);
126
+ return v === undefined ? this.get('month') : this.set('month', v);
115
127
  }
116
128
  date(v) {
117
- return v === undefined ? this.$date.getDate() : this.set('day', v);
129
+ return v === undefined ? this.get('day') : this.set('day', v);
118
130
  }
119
131
  hour(v) {
120
- return v === undefined ? this.$date.getHours() : this.set('hour', v);
132
+ return v === undefined ? this.get('hour') : this.set('hour', v);
121
133
  }
122
134
  minute(v) {
123
- return v === undefined ? this.$date.getMinutes() : this.set('minute', v);
135
+ return v === undefined ? this.get('minute') : this.set('minute', v);
124
136
  }
125
137
  second(v) {
126
- return v === undefined ? this.$date.getSeconds() : this.set('second', v);
138
+ return v === undefined ? this.get('second') : this.set('second', v);
127
139
  }
128
140
  setComponents(c, mutate = false) {
129
141
  const d = mutate ? this.$date : new Date(this.$date);
142
+ /* eslint-disable @typescript-eslint/no-unused-expressions */
130
143
  if (c.year) {
131
- d.setFullYear(c.year);
144
+ this.utcMode ? d.setUTCFullYear(c.year) : d.setFullYear(c.year);
132
145
  }
133
146
  if (c.month) {
134
- d.setMonth(c.month - 1);
147
+ this.utcMode ? d.setUTCMonth(c.month - 1) : d.setMonth(c.month - 1);
135
148
  }
136
149
  if (c.day) {
137
- d.setDate(c.day);
150
+ this.utcMode ? d.setUTCDate(c.day) : d.setDate(c.day);
138
151
  }
139
152
  if (c.hour !== undefined) {
140
- d.setHours(c.hour);
153
+ this.utcMode ? d.setUTCHours(c.hour) : d.setHours(c.hour);
141
154
  }
142
155
  if (c.minute !== undefined) {
143
- d.setMinutes(c.minute);
156
+ this.utcMode ? d.setUTCMinutes(c.minute) : d.setMinutes(c.minute);
144
157
  }
145
158
  if (c.second !== undefined) {
146
- d.setSeconds(c.second);
159
+ this.utcMode ? d.setUTCSeconds(c.second) : d.setSeconds(c.second);
147
160
  }
148
- return mutate ? this : new LocalTime(d);
161
+ /* eslint-enable @typescript-eslint/no-unused-expressions */
162
+ return mutate ? this : new LocalTime(d, this.utcMode);
149
163
  }
150
164
  add(num, unit, mutate = false) {
151
165
  return this.set(unit, this.get(unit) + num, mutate);
152
166
  }
153
167
  subtract(num, unit, mutate = false) {
154
- return this.add(-num, unit, mutate);
168
+ return this.add(num * -1, unit, mutate);
155
169
  }
156
170
  absDiff(other, unit) {
157
171
  return Math.abs(this.diff(other, unit));
@@ -189,40 +203,23 @@ class LocalTime {
189
203
  startOf(unit, mutate = false) {
190
204
  if (unit === 'second')
191
205
  return this;
192
- if (mutate) {
193
- const d = this.$date;
194
- d.setSeconds(0);
195
- if (unit === 'minute')
196
- return this;
197
- d.setMinutes(0);
198
- if (unit === 'hour')
199
- return this;
200
- d.setHours(0);
201
- if (unit === 'day')
202
- return this;
203
- d.setDate(0);
204
- if (unit === 'month')
205
- return this;
206
- d.setMonth(0);
207
- return this;
208
- }
209
- const c = this.components();
210
- c.second = 0;
211
- if (unit === 'year') {
212
- c.month = c.day = 1;
213
- c.hour = c.minute = 0;
214
- }
215
- else if (unit === 'month') {
216
- c.day = 1;
217
- c.hour = c.minute = 0;
218
- }
219
- else if (unit === 'day') {
220
- c.hour = c.minute = 0;
221
- }
222
- else if (unit === 'hour') {
223
- c.minute = 0;
224
- }
225
- return LocalTime.fromComponents(c);
206
+ const d = mutate ? this.$date : new Date(this.$date);
207
+ /* eslint-disable @typescript-eslint/no-unused-expressions */
208
+ this.utcMode ? d.setUTCSeconds(0) : d.setSeconds(0);
209
+ if (unit !== 'minute') {
210
+ this.utcMode ? d.setUTCMinutes(0) : d.setMinutes(0);
211
+ if (unit !== 'hour') {
212
+ this.utcMode ? d.setUTCHours(0) : d.setHours(0);
213
+ if (unit !== 'day') {
214
+ this.utcMode ? d.setUTCDate(0) : d.setDate(0);
215
+ if (unit !== 'month') {
216
+ this.utcMode ? d.setUTCMonth(0) : d.setMonth(0);
217
+ }
218
+ }
219
+ }
220
+ }
221
+ /* eslint-enable @typescript-eslint/no-unused-expressions */
222
+ return mutate ? this : new LocalTime(d, this.utcMode);
226
223
  }
227
224
  static sort(items, mutate = false, descending = false) {
228
225
  const mod = descending ? -1 : 1;
@@ -277,6 +274,16 @@ class LocalTime {
277
274
  }
278
275
  // todo: endOf
279
276
  components() {
277
+ if (this.utcMode) {
278
+ return {
279
+ year: this.$date.getUTCFullYear(),
280
+ month: this.$date.getUTCMonth() + 1,
281
+ day: this.$date.getUTCDate(),
282
+ hour: this.$date.getUTCHours(),
283
+ minute: this.$date.getUTCMinutes(),
284
+ second: this.$date.getSeconds(),
285
+ };
286
+ }
280
287
  return {
281
288
  year: this.$date.getFullYear(),
282
289
  month: this.$date.getMonth() + 1,
@@ -286,11 +293,20 @@ class LocalTime {
286
293
  second: this.$date.getSeconds(),
287
294
  };
288
295
  }
296
+ fromNow(now = LocalTime.now()) {
297
+ const msDiff = LocalTime.of(now).unixMillis() - this.unixMillis();
298
+ if (msDiff === 0)
299
+ return 'now';
300
+ if (msDiff >= 0) {
301
+ return `${(0, time_util_1._ms)(msDiff)} ago`;
302
+ }
303
+ return `in ${(0, time_util_1._ms)(msDiff * -1)}`;
304
+ }
289
305
  getDate() {
290
306
  return this.$date;
291
307
  }
292
308
  clone() {
293
- return new LocalTime(new Date(this.$date));
309
+ return new LocalTime(new Date(this.$date), this.utcMode);
294
310
  }
295
311
  unix() {
296
312
  return Math.floor(this.$date.valueOf() / 1000);
@@ -302,14 +318,31 @@ class LocalTime {
302
318
  return Math.floor(this.$date.valueOf() / 1000);
303
319
  }
304
320
  toLocalDate() {
321
+ if (this.utcMode) {
322
+ return localDate_1.LocalDate.create(this.$date.getUTCFullYear(), this.$date.getUTCMonth() + 1, this.$date.getUTCDate());
323
+ }
305
324
  return localDate_1.LocalDate.create(this.$date.getFullYear(), this.$date.getMonth() + 1, this.$date.getDate());
306
325
  }
307
326
  toPretty(seconds = true) {
308
- return this.$date
309
- .toISOString()
310
- .slice(0, seconds ? 19 : 16)
311
- .split('T')
312
- .join(' ');
327
+ const { year, month, day, hour, minute, second } = this.components();
328
+ return ([
329
+ String(year).padStart(4, '0'),
330
+ String(month).padStart(2, '0'),
331
+ String(day).padStart(2, '0'),
332
+ ].join('-') +
333
+ ' ' +
334
+ [
335
+ String(hour).padStart(2, '0'),
336
+ String(minute).padStart(2, '0'),
337
+ seconds && String(second).padStart(2, '0'),
338
+ ]
339
+ .filter(Boolean)
340
+ .join(':'));
341
+ // return this.$date
342
+ // .toISOString()
343
+ // .slice(0, seconds ? 19 : 16)
344
+ // .split('T')
345
+ // .join(' ')
313
346
  }
314
347
  /**
315
348
  * Returns e.g: `1984-06-21T17:56:21`, only the date part of DateTime
@@ -321,20 +354,41 @@ class LocalTime {
321
354
  * Returns e.g: `1984-06-21`, only the date part of DateTime
322
355
  */
323
356
  toISODate() {
324
- return this.$date.toISOString().slice(0, 10);
357
+ const { year, month, day } = this.components();
358
+ return [
359
+ String(year).padStart(4, '0'),
360
+ String(month).padStart(2, '0'),
361
+ String(day).padStart(2, '0'),
362
+ ].join('-');
363
+ // return this.$date.toISOString().slice(0, 10)
364
+ }
365
+ /**
366
+ * Returns e.g: `17:03:15` (or `17:03` with seconds=false)
367
+ */
368
+ toISOTime(seconds = true) {
369
+ // return this.$date.toISOString().slice(11, seconds ? 19 : 16)
370
+ const { hour, minute, second } = this.components();
371
+ return [
372
+ String(hour).padStart(2, '0'),
373
+ String(minute).padStart(2, '0'),
374
+ seconds && String(second).padStart(2, '0'),
375
+ ]
376
+ .filter(Boolean)
377
+ .join(':');
325
378
  }
326
379
  /**
327
380
  * Returns e.g: `19840621_1705`
328
381
  */
329
382
  toStringCompact(seconds = false) {
383
+ const { year, month, day, hour, minute, second } = this.components();
330
384
  return [
331
- String(this.$date.getFullYear()).padStart(4, '0'),
332
- String(this.$date.getMonth() + 1).padStart(2, '0'),
333
- String(this.$date.getDate()).padStart(2, '0'),
385
+ String(year).padStart(4, '0'),
386
+ String(month).padStart(2, '0'),
387
+ String(day).padStart(2, '0'),
334
388
  '_',
335
- String(this.$date.getHours()).padStart(2, '0'),
336
- String(this.$date.getMinutes()).padStart(2, '0'),
337
- seconds ? String(this.$date.getSeconds()).padStart(2, '0') : '',
389
+ String(hour).padStart(2, '0'),
390
+ String(minute).padStart(2, '0'),
391
+ seconds ? String(second).padStart(2, '0') : '',
338
392
  ].join('');
339
393
  }
340
394
  toString() {
@@ -36,6 +36,9 @@ export class LocalDate {
36
36
  static fromDate(d) {
37
37
  return new LocalDate(d.getFullYear(), d.getMonth() + 1, d.getDate());
38
38
  }
39
+ static fromDateUTC(d) {
40
+ return new LocalDate(d.getUTCFullYear(), d.getUTCMonth() + 1, d.getUTCDate());
41
+ }
39
42
  /**
40
43
  * Returns null if invalid.
41
44
  */
@@ -61,6 +64,9 @@ export class LocalDate {
61
64
  static today() {
62
65
  return this.fromDate(new Date());
63
66
  }
67
+ static todayUTC() {
68
+ return this.fromDateUTC(new Date());
69
+ }
64
70
  static sort(items, mutate = false, descending = false) {
65
71
  const mod = descending ? -1 : 1;
66
72
  return (mutate ? items : [...items]).sort((a, b) => a.cmp(b) * mod);
@@ -1,4 +1,5 @@
1
1
  import { _assert } from '../error/assert';
2
+ import { _ms } from '../time/time.util';
2
3
  import { LocalDate } from './localDate';
3
4
  /* eslint-disable no-dupe-class-members */
4
5
  // Design choices:
@@ -14,8 +15,9 @@ import { LocalDate } from './localDate';
14
15
  * @experimental
15
16
  */
16
17
  export class LocalTime {
17
- constructor($date) {
18
+ constructor($date, utcMode) {
18
19
  this.$date = $date;
20
+ this.utcMode = utcMode;
19
21
  }
20
22
  /**
21
23
  * Parses input String into LocalDate.
@@ -28,6 +30,14 @@ export class LocalTime {
28
30
  }
29
31
  return t;
30
32
  }
33
+ utc() {
34
+ this.utcMode = true;
35
+ return this;
36
+ }
37
+ local() {
38
+ this.utcMode = false;
39
+ return this;
40
+ }
31
41
  /**
32
42
  * Returns null if invalid
33
43
  */
@@ -49,106 +59,110 @@ export class LocalTime {
49
59
  // throw new TypeError(`Cannot parse "${d}" into LocalTime`)
50
60
  return null;
51
61
  }
52
- return new LocalTime(date);
62
+ // if (utc) {
63
+ // date.setMinutes(date.getMinutes() + date.getTimezoneOffset())
64
+ // }
65
+ return new LocalTime(date, false);
53
66
  }
54
67
  static isValid(d) {
55
68
  return this.parseOrNull(d) !== null;
56
69
  }
57
- static unix(ts) {
58
- return new LocalTime(new Date(ts * 1000));
59
- }
60
70
  static now() {
61
- return this.of(new Date());
71
+ return new LocalTime(new Date(), false);
62
72
  }
63
73
  static fromComponents(c) {
64
- return new LocalTime(new Date(c.year, c.month - 1, c.day, c.hour, c.minute, c.second));
74
+ return new LocalTime(new Date(c.year, c.month - 1, c.day, c.hour, c.minute, c.second), false);
65
75
  }
66
76
  get(unit) {
67
77
  if (unit === 'year') {
68
- return this.$date.getFullYear();
78
+ return this.utcMode ? this.$date.getUTCFullYear() : this.$date.getFullYear();
69
79
  }
70
80
  if (unit === 'month') {
71
- return this.$date.getMonth() + 1;
81
+ return (this.utcMode ? this.$date.getUTCMonth() : this.$date.getMonth()) + 1;
72
82
  }
73
83
  if (unit === 'day') {
74
- return this.$date.getDate();
84
+ return this.utcMode ? this.$date.getUTCDate() : this.$date.getDate();
75
85
  }
76
86
  if (unit === 'hour') {
77
- return this.$date.getHours();
87
+ return this.utcMode ? this.$date.getUTCHours() : this.$date.getHours();
78
88
  }
79
89
  if (unit === 'minute') {
80
- return this.$date.getMinutes();
90
+ return this.utcMode ? this.$date.getUTCMinutes() : this.$date.getMinutes();
81
91
  }
82
92
  // second
83
- return this.$date.getSeconds();
93
+ return this.utcMode ? this.$date.getUTCSeconds() : this.$date.getSeconds();
84
94
  }
85
95
  set(unit, v, mutate = false) {
86
96
  const t = mutate ? this : this.clone();
97
+ /* eslint-disable @typescript-eslint/no-unused-expressions */
87
98
  if (unit === 'year') {
88
- t.$date.setFullYear(v);
99
+ this.utcMode ? t.$date.setUTCFullYear(v) : t.$date.setFullYear(v);
89
100
  }
90
101
  else if (unit === 'month') {
91
- t.$date.setMonth(v - 1);
102
+ this.utcMode ? t.$date.setUTCMonth(v - 1) : t.$date.setMonth(v - 1);
92
103
  }
93
104
  else if (unit === 'day') {
94
- t.$date.setDate(v);
105
+ this.utcMode ? t.$date.setUTCDate(v) : t.$date.setDate(v);
95
106
  }
96
107
  else if (unit === 'hour') {
97
- t.$date.setHours(v);
108
+ this.utcMode ? t.$date.setUTCHours(v) : t.$date.setHours(v);
98
109
  }
99
110
  else if (unit === 'minute') {
100
- t.$date.setMinutes(v);
111
+ this.utcMode ? t.$date.setUTCMinutes(v) : t.$date.setMinutes(v);
101
112
  }
102
113
  else if (unit === 'second') {
103
- t.$date.setSeconds(v);
114
+ this.utcMode ? t.$date.setUTCSeconds(v) : t.$date.setSeconds(v);
104
115
  }
116
+ /* eslint-enable @typescript-eslint/no-unused-expressions */
105
117
  return t;
106
118
  }
107
119
  year(v) {
108
- return v === undefined ? this.$date.getFullYear() : this.set('year', v);
120
+ return v === undefined ? this.get('year') : this.set('year', v);
109
121
  }
110
122
  month(v) {
111
- return v === undefined ? this.$date.getMonth() + 1 : this.set('month', v);
123
+ return v === undefined ? this.get('month') : this.set('month', v);
112
124
  }
113
125
  date(v) {
114
- return v === undefined ? this.$date.getDate() : this.set('day', v);
126
+ return v === undefined ? this.get('day') : this.set('day', v);
115
127
  }
116
128
  hour(v) {
117
- return v === undefined ? this.$date.getHours() : this.set('hour', v);
129
+ return v === undefined ? this.get('hour') : this.set('hour', v);
118
130
  }
119
131
  minute(v) {
120
- return v === undefined ? this.$date.getMinutes() : this.set('minute', v);
132
+ return v === undefined ? this.get('minute') : this.set('minute', v);
121
133
  }
122
134
  second(v) {
123
- return v === undefined ? this.$date.getSeconds() : this.set('second', v);
135
+ return v === undefined ? this.get('second') : this.set('second', v);
124
136
  }
125
137
  setComponents(c, mutate = false) {
126
138
  const d = mutate ? this.$date : new Date(this.$date);
139
+ /* eslint-disable @typescript-eslint/no-unused-expressions */
127
140
  if (c.year) {
128
- d.setFullYear(c.year);
141
+ this.utcMode ? d.setUTCFullYear(c.year) : d.setFullYear(c.year);
129
142
  }
130
143
  if (c.month) {
131
- d.setMonth(c.month - 1);
144
+ this.utcMode ? d.setUTCMonth(c.month - 1) : d.setMonth(c.month - 1);
132
145
  }
133
146
  if (c.day) {
134
- d.setDate(c.day);
147
+ this.utcMode ? d.setUTCDate(c.day) : d.setDate(c.day);
135
148
  }
136
149
  if (c.hour !== undefined) {
137
- d.setHours(c.hour);
150
+ this.utcMode ? d.setUTCHours(c.hour) : d.setHours(c.hour);
138
151
  }
139
152
  if (c.minute !== undefined) {
140
- d.setMinutes(c.minute);
153
+ this.utcMode ? d.setUTCMinutes(c.minute) : d.setMinutes(c.minute);
141
154
  }
142
155
  if (c.second !== undefined) {
143
- d.setSeconds(c.second);
156
+ this.utcMode ? d.setUTCSeconds(c.second) : d.setSeconds(c.second);
144
157
  }
145
- return mutate ? this : new LocalTime(d);
158
+ /* eslint-enable @typescript-eslint/no-unused-expressions */
159
+ return mutate ? this : new LocalTime(d, this.utcMode);
146
160
  }
147
161
  add(num, unit, mutate = false) {
148
162
  return this.set(unit, this.get(unit) + num, mutate);
149
163
  }
150
164
  subtract(num, unit, mutate = false) {
151
- return this.add(-num, unit, mutate);
165
+ return this.add(num * -1, unit, mutate);
152
166
  }
153
167
  absDiff(other, unit) {
154
168
  return Math.abs(this.diff(other, unit));
@@ -186,40 +200,23 @@ export class LocalTime {
186
200
  startOf(unit, mutate = false) {
187
201
  if (unit === 'second')
188
202
  return this;
189
- if (mutate) {
190
- const d = this.$date;
191
- d.setSeconds(0);
192
- if (unit === 'minute')
193
- return this;
194
- d.setMinutes(0);
195
- if (unit === 'hour')
196
- return this;
197
- d.setHours(0);
198
- if (unit === 'day')
199
- return this;
200
- d.setDate(0);
201
- if (unit === 'month')
202
- return this;
203
- d.setMonth(0);
204
- return this;
205
- }
206
- const c = this.components();
207
- c.second = 0;
208
- if (unit === 'year') {
209
- c.month = c.day = 1;
210
- c.hour = c.minute = 0;
211
- }
212
- else if (unit === 'month') {
213
- c.day = 1;
214
- c.hour = c.minute = 0;
215
- }
216
- else if (unit === 'day') {
217
- c.hour = c.minute = 0;
218
- }
219
- else if (unit === 'hour') {
220
- c.minute = 0;
221
- }
222
- return LocalTime.fromComponents(c);
203
+ const d = mutate ? this.$date : new Date(this.$date);
204
+ /* eslint-disable @typescript-eslint/no-unused-expressions */
205
+ this.utcMode ? d.setUTCSeconds(0) : d.setSeconds(0);
206
+ if (unit !== 'minute') {
207
+ this.utcMode ? d.setUTCMinutes(0) : d.setMinutes(0);
208
+ if (unit !== 'hour') {
209
+ this.utcMode ? d.setUTCHours(0) : d.setHours(0);
210
+ if (unit !== 'day') {
211
+ this.utcMode ? d.setUTCDate(0) : d.setDate(0);
212
+ if (unit !== 'month') {
213
+ this.utcMode ? d.setUTCMonth(0) : d.setMonth(0);
214
+ }
215
+ }
216
+ }
217
+ }
218
+ /* eslint-enable @typescript-eslint/no-unused-expressions */
219
+ return mutate ? this : new LocalTime(d, this.utcMode);
223
220
  }
224
221
  static sort(items, mutate = false, descending = false) {
225
222
  const mod = descending ? -1 : 1;
@@ -274,6 +271,16 @@ export class LocalTime {
274
271
  }
275
272
  // todo: endOf
276
273
  components() {
274
+ if (this.utcMode) {
275
+ return {
276
+ year: this.$date.getUTCFullYear(),
277
+ month: this.$date.getUTCMonth() + 1,
278
+ day: this.$date.getUTCDate(),
279
+ hour: this.$date.getUTCHours(),
280
+ minute: this.$date.getUTCMinutes(),
281
+ second: this.$date.getSeconds(),
282
+ };
283
+ }
277
284
  return {
278
285
  year: this.$date.getFullYear(),
279
286
  month: this.$date.getMonth() + 1,
@@ -283,11 +290,20 @@ export class LocalTime {
283
290
  second: this.$date.getSeconds(),
284
291
  };
285
292
  }
293
+ fromNow(now = LocalTime.now()) {
294
+ const msDiff = LocalTime.of(now).unixMillis() - this.unixMillis();
295
+ if (msDiff === 0)
296
+ return 'now';
297
+ if (msDiff >= 0) {
298
+ return `${_ms(msDiff)} ago`;
299
+ }
300
+ return `in ${_ms(msDiff * -1)}`;
301
+ }
286
302
  getDate() {
287
303
  return this.$date;
288
304
  }
289
305
  clone() {
290
- return new LocalTime(new Date(this.$date));
306
+ return new LocalTime(new Date(this.$date), this.utcMode);
291
307
  }
292
308
  unix() {
293
309
  return Math.floor(this.$date.valueOf() / 1000);
@@ -299,14 +315,31 @@ export class LocalTime {
299
315
  return Math.floor(this.$date.valueOf() / 1000);
300
316
  }
301
317
  toLocalDate() {
318
+ if (this.utcMode) {
319
+ return LocalDate.create(this.$date.getUTCFullYear(), this.$date.getUTCMonth() + 1, this.$date.getUTCDate());
320
+ }
302
321
  return LocalDate.create(this.$date.getFullYear(), this.$date.getMonth() + 1, this.$date.getDate());
303
322
  }
304
323
  toPretty(seconds = true) {
305
- return this.$date
306
- .toISOString()
307
- .slice(0, seconds ? 19 : 16)
308
- .split('T')
309
- .join(' ');
324
+ const { year, month, day, hour, minute, second } = this.components();
325
+ return ([
326
+ String(year).padStart(4, '0'),
327
+ String(month).padStart(2, '0'),
328
+ String(day).padStart(2, '0'),
329
+ ].join('-') +
330
+ ' ' +
331
+ [
332
+ String(hour).padStart(2, '0'),
333
+ String(minute).padStart(2, '0'),
334
+ seconds && String(second).padStart(2, '0'),
335
+ ]
336
+ .filter(Boolean)
337
+ .join(':'));
338
+ // return this.$date
339
+ // .toISOString()
340
+ // .slice(0, seconds ? 19 : 16)
341
+ // .split('T')
342
+ // .join(' ')
310
343
  }
311
344
  /**
312
345
  * Returns e.g: `1984-06-21T17:56:21`, only the date part of DateTime
@@ -318,20 +351,41 @@ export class LocalTime {
318
351
  * Returns e.g: `1984-06-21`, only the date part of DateTime
319
352
  */
320
353
  toISODate() {
321
- return this.$date.toISOString().slice(0, 10);
354
+ const { year, month, day } = this.components();
355
+ return [
356
+ String(year).padStart(4, '0'),
357
+ String(month).padStart(2, '0'),
358
+ String(day).padStart(2, '0'),
359
+ ].join('-');
360
+ // return this.$date.toISOString().slice(0, 10)
361
+ }
362
+ /**
363
+ * Returns e.g: `17:03:15` (or `17:03` with seconds=false)
364
+ */
365
+ toISOTime(seconds = true) {
366
+ // return this.$date.toISOString().slice(11, seconds ? 19 : 16)
367
+ const { hour, minute, second } = this.components();
368
+ return [
369
+ String(hour).padStart(2, '0'),
370
+ String(minute).padStart(2, '0'),
371
+ seconds && String(second).padStart(2, '0'),
372
+ ]
373
+ .filter(Boolean)
374
+ .join(':');
322
375
  }
323
376
  /**
324
377
  * Returns e.g: `19840621_1705`
325
378
  */
326
379
  toStringCompact(seconds = false) {
380
+ const { year, month, day, hour, minute, second } = this.components();
327
381
  return [
328
- String(this.$date.getFullYear()).padStart(4, '0'),
329
- String(this.$date.getMonth() + 1).padStart(2, '0'),
330
- String(this.$date.getDate()).padStart(2, '0'),
382
+ String(year).padStart(4, '0'),
383
+ String(month).padStart(2, '0'),
384
+ String(day).padStart(2, '0'),
331
385
  '_',
332
- String(this.$date.getHours()).padStart(2, '0'),
333
- String(this.$date.getMinutes()).padStart(2, '0'),
334
- seconds ? String(this.$date.getSeconds()).padStart(2, '0') : '',
386
+ String(hour).padStart(2, '0'),
387
+ String(minute).padStart(2, '0'),
388
+ seconds ? String(second).padStart(2, '0') : '',
335
389
  ].join('');
336
390
  }
337
391
  toString() {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@naturalcycles/js-lib",
3
- "version": "14.91.2",
3
+ "version": "14.92.0",
4
4
  "scripts": {
5
5
  "prepare": "husky install",
6
6
  "build-prod": "build-prod-esm-cjs",
@@ -47,6 +47,10 @@ export class LocalDate {
47
47
  return new LocalDate(d.getFullYear(), d.getMonth() + 1, d.getDate())
48
48
  }
49
49
 
50
+ static fromDateUTC(d: Date): LocalDate {
51
+ return new LocalDate(d.getUTCFullYear(), d.getUTCMonth() + 1, d.getUTCDate())
52
+ }
53
+
50
54
  /**
51
55
  * Returns null if invalid.
52
56
  */
@@ -79,6 +83,10 @@ export class LocalDate {
79
83
  return this.fromDate(new Date())
80
84
  }
81
85
 
86
+ static todayUTC(): LocalDate {
87
+ return this.fromDateUTC(new Date())
88
+ }
89
+
82
90
  static sort(items: LocalDate[], mutate = false, descending = false): LocalDate[] {
83
91
  const mod = descending ? -1 : 1
84
92
  return (mutate ? items : [...items]).sort((a, b) => a.cmp(b) * mod)
@@ -1,4 +1,5 @@
1
1
  import { _assert } from '../error/assert'
2
+ import { _ms } from '../time/time.util'
2
3
  import { IsoDate, IsoDateTime, UnixTimestamp } from '../types'
3
4
  import { LocalDate } from './localDate'
4
5
 
@@ -30,7 +31,7 @@ export interface LocalTimeComponents {
30
31
  * @experimental
31
32
  */
32
33
  export class LocalTime {
33
- private constructor(private $date: Date) {}
34
+ private constructor(private $date: Date, public utcMode: boolean) {}
34
35
 
35
36
  /**
36
37
  * Parses input String into LocalDate.
@@ -46,6 +47,16 @@ export class LocalTime {
46
47
  return t
47
48
  }
48
49
 
50
+ utc(): this {
51
+ this.utcMode = true
52
+ return this
53
+ }
54
+
55
+ local(): this {
56
+ this.utcMode = false
57
+ return this
58
+ }
59
+
49
60
  /**
50
61
  * Returns null if invalid
51
62
  */
@@ -68,63 +79,65 @@ export class LocalTime {
68
79
  return null
69
80
  }
70
81
 
71
- return new LocalTime(date)
82
+ // if (utc) {
83
+ // date.setMinutes(date.getMinutes() + date.getTimezoneOffset())
84
+ // }
85
+
86
+ return new LocalTime(date, false)
72
87
  }
73
88
 
74
89
  static isValid(d: LocalTimeConfig): boolean {
75
90
  return this.parseOrNull(d) !== null
76
91
  }
77
92
 
78
- static unix(ts: UnixTimestamp): LocalTime {
79
- return new LocalTime(new Date(ts * 1000))
80
- }
81
-
82
93
  static now(): LocalTime {
83
- return this.of(new Date())
94
+ return new LocalTime(new Date(), false)
84
95
  }
85
96
 
86
97
  static fromComponents(
87
98
  c: { year: number; month: number } & Partial<LocalTimeComponents>,
88
99
  ): LocalTime {
89
- return new LocalTime(new Date(c.year, c.month - 1, c.day, c.hour, c.minute, c.second))
100
+ return new LocalTime(new Date(c.year, c.month - 1, c.day, c.hour, c.minute, c.second), false)
90
101
  }
91
102
 
92
103
  get(unit: LocalTimeUnit): number {
93
104
  if (unit === 'year') {
94
- return this.$date.getFullYear()
105
+ return this.utcMode ? this.$date.getUTCFullYear() : this.$date.getFullYear()
95
106
  }
96
107
  if (unit === 'month') {
97
- return this.$date.getMonth() + 1
108
+ return (this.utcMode ? this.$date.getUTCMonth() : this.$date.getMonth()) + 1
98
109
  }
99
110
  if (unit === 'day') {
100
- return this.$date.getDate()
111
+ return this.utcMode ? this.$date.getUTCDate() : this.$date.getDate()
101
112
  }
102
113
  if (unit === 'hour') {
103
- return this.$date.getHours()
114
+ return this.utcMode ? this.$date.getUTCHours() : this.$date.getHours()
104
115
  }
105
116
  if (unit === 'minute') {
106
- return this.$date.getMinutes()
117
+ return this.utcMode ? this.$date.getUTCMinutes() : this.$date.getMinutes()
107
118
  }
108
119
  // second
109
- return this.$date.getSeconds()
120
+ return this.utcMode ? this.$date.getUTCSeconds() : this.$date.getSeconds()
110
121
  }
111
122
 
112
123
  set(unit: LocalTimeUnit, v: number, mutate = false): LocalTime {
113
124
  const t = mutate ? this : this.clone()
114
125
 
126
+ /* eslint-disable @typescript-eslint/no-unused-expressions */
115
127
  if (unit === 'year') {
116
- t.$date.setFullYear(v)
128
+ this.utcMode ? t.$date.setUTCFullYear(v) : t.$date.setFullYear(v)
117
129
  } else if (unit === 'month') {
118
- t.$date.setMonth(v - 1)
130
+ this.utcMode ? t.$date.setUTCMonth(v - 1) : t.$date.setMonth(v - 1)
119
131
  } else if (unit === 'day') {
120
- t.$date.setDate(v)
132
+ this.utcMode ? t.$date.setUTCDate(v) : t.$date.setDate(v)
121
133
  } else if (unit === 'hour') {
122
- t.$date.setHours(v)
134
+ this.utcMode ? t.$date.setUTCHours(v) : t.$date.setHours(v)
123
135
  } else if (unit === 'minute') {
124
- t.$date.setMinutes(v)
136
+ this.utcMode ? t.$date.setUTCMinutes(v) : t.$date.setMinutes(v)
125
137
  } else if (unit === 'second') {
126
- t.$date.setSeconds(v)
138
+ this.utcMode ? t.$date.setUTCSeconds(v) : t.$date.setSeconds(v)
127
139
  }
140
+ /* eslint-enable @typescript-eslint/no-unused-expressions */
128
141
 
129
142
  return t
130
143
  }
@@ -132,57 +145,59 @@ export class LocalTime {
132
145
  year(): number
133
146
  year(v: number): LocalTime
134
147
  year(v?: number): number | LocalTime {
135
- return v === undefined ? this.$date.getFullYear() : this.set('year', v)
148
+ return v === undefined ? this.get('year') : this.set('year', v)
136
149
  }
137
150
  month(): number
138
151
  month(v: number): LocalTime
139
152
  month(v?: number): number | LocalTime {
140
- return v === undefined ? this.$date.getMonth() + 1 : this.set('month', v)
153
+ return v === undefined ? this.get('month') : this.set('month', v)
141
154
  }
142
155
  date(): number
143
156
  date(v: number): LocalTime
144
157
  date(v?: number): number | LocalTime {
145
- return v === undefined ? this.$date.getDate() : this.set('day', v)
158
+ return v === undefined ? this.get('day') : this.set('day', v)
146
159
  }
147
160
  hour(): number
148
161
  hour(v: number): LocalTime
149
162
  hour(v?: number): number | LocalTime {
150
- return v === undefined ? this.$date.getHours() : this.set('hour', v)
163
+ return v === undefined ? this.get('hour') : this.set('hour', v)
151
164
  }
152
165
  minute(): number
153
166
  minute(v: number): LocalTime
154
167
  minute(v?: number): number | LocalTime {
155
- return v === undefined ? this.$date.getMinutes() : this.set('minute', v)
168
+ return v === undefined ? this.get('minute') : this.set('minute', v)
156
169
  }
157
170
  second(): number
158
171
  second(v: number): LocalTime
159
172
  second(v?: number): number | LocalTime {
160
- return v === undefined ? this.$date.getSeconds() : this.set('second', v)
173
+ return v === undefined ? this.get('second') : this.set('second', v)
161
174
  }
162
175
 
163
176
  setComponents(c: Partial<LocalTimeComponents>, mutate = false): LocalTime {
164
177
  const d = mutate ? this.$date : new Date(this.$date)
165
178
 
179
+ /* eslint-disable @typescript-eslint/no-unused-expressions */
166
180
  if (c.year) {
167
- d.setFullYear(c.year)
181
+ this.utcMode ? d.setUTCFullYear(c.year) : d.setFullYear(c.year)
168
182
  }
169
183
  if (c.month) {
170
- d.setMonth(c.month - 1)
184
+ this.utcMode ? d.setUTCMonth(c.month - 1) : d.setMonth(c.month - 1)
171
185
  }
172
186
  if (c.day) {
173
- d.setDate(c.day)
187
+ this.utcMode ? d.setUTCDate(c.day) : d.setDate(c.day)
174
188
  }
175
189
  if (c.hour !== undefined) {
176
- d.setHours(c.hour)
190
+ this.utcMode ? d.setUTCHours(c.hour) : d.setHours(c.hour)
177
191
  }
178
192
  if (c.minute !== undefined) {
179
- d.setMinutes(c.minute)
193
+ this.utcMode ? d.setUTCMinutes(c.minute) : d.setMinutes(c.minute)
180
194
  }
181
195
  if (c.second !== undefined) {
182
- d.setSeconds(c.second)
196
+ this.utcMode ? d.setUTCSeconds(c.second) : d.setSeconds(c.second)
183
197
  }
198
+ /* eslint-enable @typescript-eslint/no-unused-expressions */
184
199
 
185
- return mutate ? this : new LocalTime(d)
200
+ return mutate ? this : new LocalTime(d, this.utcMode)
186
201
  }
187
202
 
188
203
  add(num: number, unit: LocalTimeUnit, mutate = false): LocalTime {
@@ -190,7 +205,7 @@ export class LocalTime {
190
205
  }
191
206
 
192
207
  subtract(num: number, unit: LocalTimeUnit, mutate = false): LocalTime {
193
- return this.add(-num, unit, mutate)
208
+ return this.add(num * -1, unit, mutate)
194
209
  }
195
210
 
196
211
  absDiff(other: LocalTimeConfig, unit: LocalTimeUnit): number {
@@ -233,36 +248,25 @@ export class LocalTime {
233
248
  startOf(unit: LocalTimeUnit, mutate = false): LocalTime {
234
249
  if (unit === 'second') return this
235
250
 
236
- if (mutate) {
237
- const d = this.$date
238
- d.setSeconds(0)
239
- if (unit === 'minute') return this
240
- d.setMinutes(0)
241
- if (unit === 'hour') return this
242
- d.setHours(0)
243
- if (unit === 'day') return this
244
- d.setDate(0)
245
- if (unit === 'month') return this
246
- d.setMonth(0)
247
- return this
248
- }
249
-
250
- const c = this.components()
251
+ const d = mutate ? this.$date : new Date(this.$date)
251
252
 
252
- c.second = 0
253
- if (unit === 'year') {
254
- c.month = c.day = 1
255
- c.hour = c.minute = 0
256
- } else if (unit === 'month') {
257
- c.day = 1
258
- c.hour = c.minute = 0
259
- } else if (unit === 'day') {
260
- c.hour = c.minute = 0
261
- } else if (unit === 'hour') {
262
- c.minute = 0
253
+ /* eslint-disable @typescript-eslint/no-unused-expressions */
254
+ this.utcMode ? d.setUTCSeconds(0) : d.setSeconds(0)
255
+ if (unit !== 'minute') {
256
+ this.utcMode ? d.setUTCMinutes(0) : d.setMinutes(0)
257
+ if (unit !== 'hour') {
258
+ this.utcMode ? d.setUTCHours(0) : d.setHours(0)
259
+ if (unit !== 'day') {
260
+ this.utcMode ? d.setUTCDate(0) : d.setDate(0)
261
+ if (unit !== 'month') {
262
+ this.utcMode ? d.setUTCMonth(0) : d.setMonth(0)
263
+ }
264
+ }
265
+ }
263
266
  }
267
+ /* eslint-enable @typescript-eslint/no-unused-expressions */
264
268
 
265
- return LocalTime.fromComponents(c)
269
+ return mutate ? this : new LocalTime(d, this.utcMode)
266
270
  }
267
271
 
268
272
  static sort(items: LocalTime[], mutate = false, descending = false): LocalTime[] {
@@ -330,6 +334,17 @@ export class LocalTime {
330
334
  // todo: endOf
331
335
 
332
336
  components(): LocalTimeComponents {
337
+ if (this.utcMode) {
338
+ return {
339
+ year: this.$date.getUTCFullYear(),
340
+ month: this.$date.getUTCMonth() + 1,
341
+ day: this.$date.getUTCDate(),
342
+ hour: this.$date.getUTCHours(),
343
+ minute: this.$date.getUTCMinutes(),
344
+ second: this.$date.getSeconds(),
345
+ }
346
+ }
347
+
333
348
  return {
334
349
  year: this.$date.getFullYear(),
335
350
  month: this.$date.getMonth() + 1,
@@ -340,12 +355,24 @@ export class LocalTime {
340
355
  }
341
356
  }
342
357
 
358
+ fromNow(now: LocalTimeConfig = LocalTime.now()): string {
359
+ const msDiff = LocalTime.of(now).unixMillis() - this.unixMillis()
360
+
361
+ if (msDiff === 0) return 'now'
362
+
363
+ if (msDiff >= 0) {
364
+ return `${_ms(msDiff)} ago`
365
+ }
366
+
367
+ return `in ${_ms(msDiff * -1)}`
368
+ }
369
+
343
370
  getDate(): Date {
344
371
  return this.$date
345
372
  }
346
373
 
347
374
  clone(): LocalTime {
348
- return new LocalTime(new Date(this.$date))
375
+ return new LocalTime(new Date(this.$date), this.utcMode)
349
376
  }
350
377
 
351
378
  unix(): UnixTimestamp {
@@ -361,6 +388,14 @@ export class LocalTime {
361
388
  }
362
389
 
363
390
  toLocalDate(): LocalDate {
391
+ if (this.utcMode) {
392
+ return LocalDate.create(
393
+ this.$date.getUTCFullYear(),
394
+ this.$date.getUTCMonth() + 1,
395
+ this.$date.getUTCDate(),
396
+ )
397
+ }
398
+
364
399
  return LocalDate.create(
365
400
  this.$date.getFullYear(),
366
401
  this.$date.getMonth() + 1,
@@ -369,11 +404,29 @@ export class LocalTime {
369
404
  }
370
405
 
371
406
  toPretty(seconds = true): IsoDateTime {
372
- return this.$date
373
- .toISOString()
374
- .slice(0, seconds ? 19 : 16)
375
- .split('T')
376
- .join(' ')
407
+ const { year, month, day, hour, minute, second } = this.components()
408
+
409
+ return (
410
+ [
411
+ String(year).padStart(4, '0'),
412
+ String(month).padStart(2, '0'),
413
+ String(day).padStart(2, '0'),
414
+ ].join('-') +
415
+ ' ' +
416
+ [
417
+ String(hour).padStart(2, '0'),
418
+ String(minute).padStart(2, '0'),
419
+ seconds && String(second).padStart(2, '0'),
420
+ ]
421
+ .filter(Boolean)
422
+ .join(':')
423
+ )
424
+
425
+ // return this.$date
426
+ // .toISOString()
427
+ // .slice(0, seconds ? 19 : 16)
428
+ // .split('T')
429
+ // .join(' ')
377
430
  }
378
431
 
379
432
  /**
@@ -387,21 +440,47 @@ export class LocalTime {
387
440
  * Returns e.g: `1984-06-21`, only the date part of DateTime
388
441
  */
389
442
  toISODate(): IsoDate {
390
- return this.$date.toISOString().slice(0, 10)
443
+ const { year, month, day } = this.components()
444
+
445
+ return [
446
+ String(year).padStart(4, '0'),
447
+ String(month).padStart(2, '0'),
448
+ String(day).padStart(2, '0'),
449
+ ].join('-')
450
+
451
+ // return this.$date.toISOString().slice(0, 10)
452
+ }
453
+
454
+ /**
455
+ * Returns e.g: `17:03:15` (or `17:03` with seconds=false)
456
+ */
457
+ toISOTime(seconds = true): string {
458
+ // return this.$date.toISOString().slice(11, seconds ? 19 : 16)
459
+ const { hour, minute, second } = this.components()
460
+
461
+ return [
462
+ String(hour).padStart(2, '0'),
463
+ String(minute).padStart(2, '0'),
464
+ seconds && String(second).padStart(2, '0'),
465
+ ]
466
+ .filter(Boolean)
467
+ .join(':')
391
468
  }
392
469
 
393
470
  /**
394
471
  * Returns e.g: `19840621_1705`
395
472
  */
396
473
  toStringCompact(seconds = false): string {
474
+ const { year, month, day, hour, minute, second } = this.components()
475
+
397
476
  return [
398
- String(this.$date.getFullYear()).padStart(4, '0'),
399
- String(this.$date.getMonth() + 1).padStart(2, '0'),
400
- String(this.$date.getDate()).padStart(2, '0'),
477
+ String(year).padStart(4, '0'),
478
+ String(month).padStart(2, '0'),
479
+ String(day).padStart(2, '0'),
401
480
  '_',
402
- String(this.$date.getHours()).padStart(2, '0'),
403
- String(this.$date.getMinutes()).padStart(2, '0'),
404
- seconds ? String(this.$date.getSeconds()).padStart(2, '0') : '',
481
+ String(hour).padStart(2, '0'),
482
+ String(minute).padStart(2, '0'),
483
+ seconds ? String(second).padStart(2, '0') : '',
405
484
  ].join('')
406
485
  }
407
486