firefly-compiler 0.5.48 → 0.5.49

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.
Files changed (94) hide show
  1. package/bin/firefly.mjs +1 -1
  2. package/compiler/Compiler.ff +1 -1
  3. package/core/BrowserSystem.ff +5 -0
  4. package/core/Date.ff +623 -0
  5. package/core/Instant.ff +0 -24
  6. package/core/JsValue.ff +1 -1
  7. package/core/Map.ff +8 -0
  8. package/core/NodeSystem.ff +5 -0
  9. package/core/Path.ff +2 -2
  10. package/core/Random.ff +0 -4
  11. package/core/RbMap.ff +16 -0
  12. package/core/Set.ff +3 -1
  13. package/core/Task.ff +0 -4
  14. package/experimental/tests/TestDate.ff +10 -0
  15. package/experimental/tests/TestEmailAlertDateLogic.ff +84 -0
  16. package/firefly.sh +5 -5
  17. package/output/js/ff/compiler/Builder.mjs +2 -2
  18. package/output/js/ff/compiler/Compiler.mjs +3 -3
  19. package/output/js/ff/compiler/Dependencies.mjs +2 -2
  20. package/output/js/ff/compiler/DependencyLock.mjs +2 -2
  21. package/output/js/ff/compiler/Deriver.mjs +2 -2
  22. package/output/js/ff/compiler/Dictionaries.mjs +2 -2
  23. package/output/js/ff/compiler/Environment.mjs +2 -2
  24. package/output/js/ff/compiler/Inference.mjs +2 -2
  25. package/output/js/ff/compiler/JsEmitter.mjs +2 -2
  26. package/output/js/ff/compiler/JsImporter.mjs +2 -2
  27. package/output/js/ff/compiler/LspHook.mjs +2 -2
  28. package/output/js/ff/compiler/Main.mjs +2 -2
  29. package/output/js/ff/compiler/ModuleCache.mjs +2 -2
  30. package/output/js/ff/compiler/Parser.mjs +2 -2
  31. package/output/js/ff/compiler/Patterns.mjs +2 -2
  32. package/output/js/ff/compiler/Resolver.mjs +2 -2
  33. package/output/js/ff/compiler/Substitution.mjs +2 -2
  34. package/output/js/ff/compiler/Syntax.mjs +2 -2
  35. package/output/js/ff/compiler/Token.mjs +2 -2
  36. package/output/js/ff/compiler/Tokenizer.mjs +2 -2
  37. package/output/js/ff/compiler/Unification.mjs +2 -2
  38. package/output/js/ff/compiler/Wildcards.mjs +2 -2
  39. package/output/js/ff/compiler/Workspace.mjs +2 -2
  40. package/output/js/ff/core/Any.mjs +2 -2
  41. package/output/js/ff/core/Array.mjs +2 -2
  42. package/output/js/ff/core/AssetSystem.mjs +2 -2
  43. package/output/js/ff/core/Atomic.mjs +2 -2
  44. package/output/js/ff/core/Bool.mjs +2 -2
  45. package/output/js/ff/core/BrowserSystem.mjs +28 -2
  46. package/output/js/ff/core/Buffer.mjs +2 -2
  47. package/output/js/ff/core/BuildSystem.mjs +2 -2
  48. package/output/js/ff/core/Channel.mjs +2 -2
  49. package/output/js/ff/core/Char.mjs +2 -2
  50. package/output/js/ff/core/Core.mjs +2 -2
  51. package/output/js/ff/core/Crypto.mjs +2 -2
  52. package/output/js/ff/core/Date.mjs +1009 -0
  53. package/output/js/ff/core/Duration.mjs +2 -2
  54. package/output/js/ff/core/Equal.mjs +2 -2
  55. package/output/js/ff/core/Error.mjs +2 -2
  56. package/output/js/ff/core/FileHandle.mjs +2 -2
  57. package/output/js/ff/core/Float.mjs +2 -2
  58. package/output/js/ff/core/HttpClient.mjs +2 -2
  59. package/output/js/ff/core/Int.mjs +2 -2
  60. package/output/js/ff/core/IntMap.mjs +2 -2
  61. package/output/js/ff/core/Js.mjs +2 -2
  62. package/output/js/ff/core/JsSystem.mjs +2 -2
  63. package/output/js/ff/core/JsValue.mjs +3 -3
  64. package/output/js/ff/core/Json.mjs +2 -2
  65. package/output/js/ff/core/List.mjs +2 -2
  66. package/output/js/ff/core/Lock.mjs +2 -2
  67. package/output/js/ff/core/Log.mjs +2 -2
  68. package/output/js/ff/core/Map.mjs +18 -2
  69. package/output/js/ff/core/NodeSystem.mjs +28 -2
  70. package/output/js/ff/core/Nothing.mjs +2 -2
  71. package/output/js/ff/core/Option.mjs +2 -2
  72. package/output/js/ff/core/Ordering.mjs +2 -2
  73. package/output/js/ff/core/Pair.mjs +2 -2
  74. package/output/js/ff/core/Path.mjs +4 -4
  75. package/output/js/ff/core/Queue.mjs +2 -2
  76. package/output/js/ff/core/Random.mjs +2 -10
  77. package/output/js/ff/core/RbMap.mjs +74 -2
  78. package/output/js/ff/core/Serializable.mjs +2 -2
  79. package/output/js/ff/core/Set.mjs +26 -2
  80. package/output/js/ff/core/Show.mjs +2 -2
  81. package/output/js/ff/core/SourceLocation.mjs +2 -2
  82. package/output/js/ff/core/Stream.mjs +2 -2
  83. package/output/js/ff/core/String.mjs +2 -2
  84. package/output/js/ff/core/StringMap.mjs +2 -2
  85. package/output/js/ff/core/Task.mjs +2 -10
  86. package/output/js/ff/core/Try.mjs +2 -2
  87. package/output/js/ff/core/Unit.mjs +2 -2
  88. package/package.json +1 -1
  89. package/postgresql/Pg.ff +0 -40
  90. package/s3/S3.ff +4 -4
  91. package/vscode/package.json +1 -1
  92. package/experimental/IfBug.ff +0 -8
  93. package/output/js/ff/core/Instant.mjs +0 -149
  94. /package/fireflysite/assets/markdown/scratch/{Toc.md → toc.md} +0 -0
package/bin/firefly.mjs CHANGED
@@ -1,2 +1,2 @@
1
- #!/usr/bin/env node
1
+ #!/usr/bin/env node --harmony-temporal
2
2
  import * as firefly from '../output/js/ff/compiler/Main.mjs';
@@ -67,13 +67,13 @@ coreImports: List[DImport] =
67
67
  "Char"
68
68
  "Core"
69
69
  "Crypto"
70
+ "Date"
70
71
  "Duration"
71
72
  "Equal"
72
73
  "Error"
73
74
  "FileHandle"
74
75
  "Float"
75
76
  "HttpClient"
76
- "Instant"
77
77
  "Int"
78
78
  "IntMap"
79
79
  "Json"
@@ -18,6 +18,11 @@ extend self: BrowserSystem {
18
18
  Js.globalThis()?
19
19
  }
20
20
 
21
+ date(timeZoneId: Option[String] = None, calendarId: String = Date.isoCalendarId): Date {
22
+ let date = Date(Js->Temporal->Now->zonedDateTimeISO(timeZoneId.map {_!}.else {Js.undefined()}))
23
+ if(calendarId == Date.isoCalendarId) {date} else {date.withCalendar(calendarId)}
24
+ }
25
+
21
26
  url(): String {
22
27
  Js->location->href?
23
28
  }
package/core/Date.ff ADDED
@@ -0,0 +1,623 @@
1
+ // Temporal.ZonedDateTime but with consistent equals/compare
2
+ newtype Date(jsValue: JsValue)
3
+
4
+ data DateGap(
5
+ years: Int = 0
6
+ months: Int = 0
7
+ weeks: Int = 0
8
+ days: Int = 0
9
+ hours: Int = 0
10
+ minutes: Int = 0
11
+ seconds: Int = 0
12
+ milliseconds: Int = 0
13
+ microseconds: Int = 0
14
+ nanoseconds: Int = 0
15
+ )
16
+
17
+ new(
18
+ timeZoneId: String
19
+ year: Int
20
+ month: Int
21
+ day: Int
22
+ hour: Int = 0
23
+ minute: Int = 0
24
+ second: Int = 0
25
+ millisecond: Int = 0
26
+ microsecond: Int = 0
27
+ nanosecond: Int = 0
28
+ calendarId: String = "iso8601"
29
+ offset: Option[String] = None
30
+ earlier: Bool = True
31
+ later: Bool = True
32
+ ): Date {
33
+ Date(Js->Temporal->ZonedDateTime->from(Js->(
34
+ timeZone = timeZoneId
35
+ year = year
36
+ month = month
37
+ day = day
38
+ hour = hour
39
+ minute = minute
40
+ second = second
41
+ millisecond = millisecond
42
+ microsecond = microsecond
43
+ nanosecond = nanosecond
44
+ calendar = calendarId
45
+ offset = offset.map {_!}.else {Js.undefined()}
46
+ ), internalDisambiguation(earlier, later)))
47
+ }
48
+
49
+ newEra(
50
+ calendarId: String
51
+ timeZoneId: String
52
+ era: String
53
+ eraYear: Int
54
+ month: Int
55
+ day: Int
56
+ hour: Int = 0
57
+ minute: Int = 0
58
+ second: Int = 0
59
+ millisecond: Int = 0
60
+ microsecond: Int = 0
61
+ nanosecond: Int = 0
62
+ offset: Option[String] = None
63
+ earlier: Bool = True
64
+ later: Bool = True
65
+ ): Date {
66
+ Date(Js->Temporal->ZonedDateTime->from(Js->(
67
+ timeZone = timeZoneId
68
+ era = era
69
+ eraYear = eraYear
70
+ month = month
71
+ day = day
72
+ hour = hour
73
+ minute = minute
74
+ second = second
75
+ millisecond = millisecond
76
+ microsecond = microsecond
77
+ nanosecond = nanosecond
78
+ calendar = calendarId
79
+ offset = offset.map {_!}.else {Js.undefined()}
80
+ ), internalDisambiguation(earlier, later)))
81
+ }
82
+
83
+ newEpochMilliseconds(timeZoneId: String, epochMilliseconds: Int, calendarId: String = "iso8601"): Date {
84
+ let zoned = Js->Temporal->Instant->fromEpochMilliseconds(epochMilliseconds)->toZonedDateTimeISO(timeZoneId)
85
+ if(calendarId != "iso8601") {Date(zoned->withCalendar(calendarId))} else {Date(zoned)}
86
+ }
87
+
88
+ newRfc9557(rfc9557: String): Date {
89
+ Date(Js->Temporal->ZonedDateTime->from(rfc9557))
90
+ }
91
+
92
+ gap(iso8601: String): DateGap {
93
+ let duration = Js->Temporal->Duration->from(iso8601)
94
+ DateGap(
95
+ years = duration->years?
96
+ months = duration->months?
97
+ weeks = duration->weeks?
98
+ days = duration->days?
99
+ hours = duration->hours?
100
+ minutes = duration->minutes?
101
+ seconds = duration->seconds?
102
+ milliseconds = duration->milliseconds?
103
+ microseconds = duration->microseconds?
104
+ nanoseconds = duration->nanoseconds?
105
+ )
106
+ }
107
+
108
+ instance Date: Equal {
109
+ equals(x: Date, y: Date): Bool {
110
+ x.jsValue->equals(y.jsValue)?
111
+ }
112
+ }
113
+
114
+ instance Date: Order {
115
+ compare(x: Date, y: Date): Ordering {
116
+ let instant: Int = Js->Temporal->ZonedDateTime->compare(x.jsValue, y.jsValue)?
117
+ if(instant != 0) {Ordering.fromInt(instant)} else:
118
+ let timeZone = Ordering.compare(x.timeZoneId(), y.timeZoneId())
119
+ if(timeZone != OrderingSame) {timeZone} else:
120
+ Ordering.compare(x.calendarId(), y.calendarId())
121
+ }
122
+ }
123
+
124
+ instance Date: HasAnyTag {
125
+ anyTag(): AnyTag[Date] {
126
+ Any.internalAnyTag("ff:core/Date.Date[]")
127
+ }
128
+ }
129
+
130
+ instance Date: Show {
131
+ show(value: Date): String {
132
+ value.toRfc9557()
133
+ }
134
+ }
135
+
136
+ instance Date: Serializable {
137
+
138
+ serializeUsing(serialization: Serialization, value: Date): Unit {
139
+ Serializable.serializeUsing(serialization, value.toRfc9557())
140
+ }
141
+
142
+ deserializeUsing(serialization: Serialization): Date {
143
+ newRfc9557(Serializable.deserializeUsing(serialization))
144
+ }
145
+
146
+ }
147
+
148
+ extend self: Date {
149
+
150
+ timeZoneId(): String {
151
+ self.jsValue->timeZoneId?
152
+ }
153
+
154
+ calendarId(): String {
155
+ self.jsValue->calendarId?
156
+ }
157
+
158
+ day(): Int {
159
+ self.jsValue->day?
160
+ }
161
+
162
+ dayOfWeek(): Int {
163
+ self.jsValue->dayOfWeek?
164
+ }
165
+
166
+ dayOfYear(): Int {
167
+ self.jsValue->dayOfYear?
168
+ }
169
+
170
+ daysInWeek(): Int {
171
+ self.jsValue->daysInWeek?
172
+ }
173
+
174
+ daysInMonth(): Int {
175
+ self.jsValue->daysInMonth?
176
+ }
177
+
178
+ daysInYear(): Int {
179
+ self.jsValue->daysInYear?
180
+ }
181
+
182
+ epochMilliseconds(): Int {
183
+ self.jsValue->epochMilliseconds?
184
+ }
185
+
186
+ era(): Option[String] {
187
+ let era = self.jsValue->era
188
+ if(!era.isNullOrUndefined()) {era?}
189
+ }
190
+
191
+ eraYear(): Option[Int] {
192
+ let eraYear = self.jsValue->eraYear
193
+ if(!eraYear.isNullOrUndefined()) {eraYear?}
194
+ }
195
+
196
+ hour(): Int {
197
+ self.jsValue->hour?
198
+ }
199
+
200
+ hoursInDay(): Int {
201
+ self.jsValue->hoursInDay?
202
+ }
203
+
204
+ inLeapYear(): Bool {
205
+ self.jsValue->inLeapYear?
206
+ }
207
+
208
+ microsecond(): Int {
209
+ self.jsValue->microsecond?
210
+ }
211
+
212
+ millisecond(): Int {
213
+ self.jsValue->millisecond?
214
+ }
215
+
216
+ minute(): Int {
217
+ self.jsValue->minute?
218
+ }
219
+
220
+ month(): Int {
221
+ self.jsValue->month?
222
+ }
223
+
224
+ monthCode(): String {
225
+ self.jsValue->monthCode?
226
+ }
227
+
228
+ monthsInYear(): Int {
229
+ self.jsValue->monthsInYear?
230
+ }
231
+
232
+ nanosecond(): Int {
233
+ self.jsValue->nanosecond?
234
+ }
235
+
236
+ offset(): String {
237
+ self.jsValue->offset?
238
+ }
239
+
240
+ offsetNanoseconds(): Int {
241
+ self.jsValue->offsetNanoseconds?
242
+ }
243
+
244
+ second(): Int {
245
+ self.jsValue->second?
246
+ }
247
+
248
+ weekOfYear(): Int {
249
+ self.jsValue->weekOfYear?
250
+ }
251
+
252
+ year(): Int {
253
+ self.jsValue->year?
254
+ }
255
+
256
+ yearOfWeek(): Int {
257
+ self.jsValue->yearOfWeek?
258
+ }
259
+
260
+ nextTimeZoneTransition(): Date {
261
+ Date(self.jsValue->getTimeZoneTransition("next"))
262
+ }
263
+
264
+ previousTimeZoneTransition(): Date {
265
+ Date(self.jsValue->getTimeZoneTransition("previous"))
266
+ }
267
+
268
+ startOfYear(): Date {
269
+ Date(self.jsValue->with(Js->(year = self.year(), month = 1, day = 1))->startOfDay())
270
+ }
271
+
272
+ startOfMonth(): Date {
273
+ Date(self.jsValue->with(Js->(year = self.year(), month = self.month(), day = 1))->startOfDay())
274
+ }
275
+
276
+ startOfWeek(firstDayOfWeek: Int = 1): Date {
277
+ let offset = ((self.dayOfWeek() - firstDayOfWeek) + self.daysInWeek()) % self.daysInWeek()
278
+ Date(self.jsValue->subtract(Js->(day = offset))->startOfDay())
279
+ }
280
+
281
+ startOfDay(): Date {
282
+ Date(self.jsValue->startOfDay())
283
+ }
284
+
285
+ startOfHour(): Date {
286
+ Date(self.jsValue->round(Js->(smallestUnit = "hour", roundingMode = "floor")))
287
+ }
288
+
289
+ startOfMinute(): Date {
290
+ Date(self.jsValue->round(Js->(smallestUnit = "minute", roundingMode = "floor")))
291
+ }
292
+
293
+ startOfSecond(): Date {
294
+ Date(self.jsValue->round(Js->(smallestUnit = "second", roundingMode = "floor")))
295
+ }
296
+
297
+ startOfMillisecond(): Date {
298
+ Date(self.jsValue->round(Js->(smallestUnit = "millisecond", roundingMode = "floor")))
299
+ }
300
+
301
+ startOfMicrosecond(): Date {
302
+ Date(self.jsValue->round(Js->(smallestUnit = "microsecond", roundingMode = "floor")))
303
+ }
304
+
305
+ toRfc9557(
306
+ smallestUnit: Option[String] = None
307
+ fractionalSecondDigits: Option[Int] = None
308
+ timeZone: Bool = True
309
+ offset: Bool = True
310
+ calendar: Bool = True
311
+ ): String {
312
+ self.jsValue->toString(Js->(
313
+ calendarName = if(calendar) {"auto"} else {"never"}
314
+ fractionalSecondDigits = fractionalSecondDigits.map {_!}.else {"auto"!}
315
+ smallestUnit = smallestUnit.map {_!}.else {Js.undefined()}
316
+ timeZoneName = if(timeZone) {"auto"} else {"never"}
317
+ offset = if(offset) {"auto"} else {"never"}
318
+ ))?
319
+ }
320
+
321
+ withCalendar(calendarId: String): Date {
322
+ Date(self.jsValue->withCalendar(calendarId))
323
+ }
324
+
325
+ withTimeZone(timeZoneId: String): Date {
326
+ Date(self.jsValue->withTimeZone(timeZoneId))
327
+ }
328
+
329
+ withEra(
330
+ era: String
331
+ eraYear: Int
332
+ monthCode: Option[String] = None
333
+ day: Option[Int] = None
334
+ earlier: Bool = True
335
+ later: Bool = True
336
+ ): Date {
337
+ Date(self.jsValue->with(Js->(
338
+ era = era
339
+ eraYear = eraYear
340
+ monthCode = monthCode.map {_!}.else {Js.undefined()}
341
+ day = day.map {_!}.else {Js.undefined()}
342
+ ), internalDisambiguation(earlier, later)))
343
+ }
344
+
345
+ withMonthCode(
346
+ monthCode: String
347
+ day: Option[Int] = None
348
+ earlier: Bool = True
349
+ later: Bool = True
350
+ ): Date {
351
+ Date(self.jsValue->with(Js->(
352
+ monthCode = monthCode
353
+ day = day.map {_!}.else {Js.undefined()}
354
+ ), internalDisambiguation(earlier, later)))
355
+ }
356
+
357
+ with(
358
+ year: Option[Int] = None
359
+ month: Option[Int] = None
360
+ week: Option[Int] = None
361
+ day: Option[Int] = None
362
+ hour: Option[Int] = None
363
+ minute: Option[Int] = None
364
+ second: Option[Int] = None
365
+ millisecond: Option[Int] = None
366
+ microsecond: Option[Int] = None
367
+ nanosecond: Option[Int] = None
368
+ offset: Option[String] = None
369
+ earlier: Bool = True
370
+ later: Bool = True
371
+ ): Date {
372
+ Date(self.jsValue->with(Js->(
373
+ year = year.map {_!}.else {Js.undefined()}
374
+ month = month.map {_!}.else {Js.undefined()}
375
+ week = week.map {_!}.else {Js.undefined()}
376
+ day = day.map {_!}.else {Js.undefined()}
377
+ hour = hour.map {_!}.else {Js.undefined()}
378
+ minute = minute.map {_!}.else {Js.undefined()}
379
+ second = second.map {_!}.else {Js.undefined()}
380
+ millisecond = millisecond.map {_!}.else {Js.undefined()}
381
+ microsecond = microsecond.map {_!}.else {Js.undefined()}
382
+ nanosecond = nanosecond.map {_!}.else {Js.undefined()}
383
+ offset = offset.map {_!}.else {Js.undefined()}
384
+ ), internalDisambiguation(earlier, later)))
385
+ }
386
+
387
+ add(
388
+ years: Int = 0
389
+ months: Int = 0
390
+ weeks: Int = 0
391
+ days: Int = 0
392
+ hours: Int = 0
393
+ minutes: Int = 0
394
+ seconds: Int = 0
395
+ milliseconds: Int = 0
396
+ microseconds: Int = 0
397
+ nanoseconds: Int = 0
398
+ ): Date {
399
+ Date(self.jsValue->add(Js->(
400
+ years = years
401
+ months = months
402
+ weeks = weeks
403
+ days = days
404
+ hours = hours
405
+ minutes = minutes
406
+ seconds = seconds
407
+ milliseconds = milliseconds
408
+ microseconds = microseconds
409
+ nanoseconds = nanoseconds
410
+ )))
411
+ }
412
+
413
+ subtract(
414
+ years: Int = 0
415
+ months: Int = 0
416
+ weeks: Int = 0
417
+ days: Int = 0
418
+ hours: Int = 0
419
+ minutes: Int = 0
420
+ seconds: Int = 0
421
+ milliseconds: Int = 0
422
+ microseconds: Int = 0
423
+ nanoseconds: Int = 0
424
+ ): Date {
425
+ Date(self.jsValue->subtract(Js->(
426
+ years = years
427
+ months = months
428
+ weeks = weeks
429
+ days = days
430
+ hours = hours
431
+ minutes = minutes
432
+ seconds = seconds
433
+ milliseconds = milliseconds
434
+ microseconds = microseconds
435
+ nanoseconds = nanoseconds
436
+ )))
437
+ }
438
+
439
+ addGap(gap: DateGap): Date {
440
+ Date(self.jsValue->add(Js->(
441
+ years = gap.years
442
+ months = gap.months
443
+ weeks = gap.weeks
444
+ days = gap.days
445
+ hours = gap.hours
446
+ minutes = gap.minutes
447
+ seconds = gap.seconds
448
+ milliseconds = gap.milliseconds
449
+ microseconds = gap.microseconds
450
+ nanoseconds = gap.nanoseconds
451
+ )))
452
+ }
453
+
454
+ subtractGap(gap: DateGap): Date {
455
+ Date(self.jsValue->add(Js->(
456
+ years = gap.years
457
+ months = gap.months
458
+ weeks = gap.weeks
459
+ days = gap.days
460
+ hours = gap.hours
461
+ minutes = gap.minutes
462
+ seconds = gap.seconds
463
+ milliseconds = gap.milliseconds
464
+ microseconds = gap.microseconds
465
+ nanoseconds = gap.nanoseconds
466
+ )))
467
+ }
468
+
469
+ since(that: Date): DateGap {
470
+ let duration = self.jsValue->since(that.jsValue)
471
+ DateGap(
472
+ years = duration->years?
473
+ months = duration->months?
474
+ weeks = duration->weeks?
475
+ days = duration->days?
476
+ hours = duration->hours?
477
+ minutes = duration->minutes?
478
+ seconds = duration->seconds?
479
+ milliseconds = duration->milliseconds?
480
+ microseconds = duration->microseconds?
481
+ nanoseconds = duration->nanoseconds?
482
+ )
483
+ }
484
+
485
+ until(that: Date): DateGap {
486
+ let duration = self.jsValue->until(that.jsValue)
487
+ DateGap(
488
+ years = duration->years?
489
+ months = duration->months?
490
+ weeks = duration->weeks?
491
+ days = duration->days?
492
+ hours = duration->hours?
493
+ minutes = duration->minutes?
494
+ seconds = duration->seconds?
495
+ milliseconds = duration->milliseconds?
496
+ microseconds = duration->microseconds?
497
+ nanoseconds = duration->nanoseconds?
498
+ )
499
+ }
500
+
501
+ yearsSince(that: Date): Float {
502
+ let duration = self.jsValue->since(that.jsValue)
503
+ duration->total(Js->(unit = "years", relativeTo = that.jsValue))?
504
+ }
505
+
506
+ monthsSince(that: Date): Float {
507
+ let duration = self.jsValue->since(that.jsValue)
508
+ duration->total(Js->(unit = "months", relativeTo = that.jsValue))?
509
+ }
510
+
511
+ weeksSince(that: Date): Float {
512
+ let duration = self.jsValue->since(that.jsValue)
513
+ duration->total(Js->(unit = "weeks", relativeTo = that.jsValue))?
514
+ }
515
+
516
+ daysSince(that: Date): Float {
517
+ let duration = self.jsValue->since(that.jsValue)
518
+ duration->total(Js->(unit = "days", relativeTo = that.jsValue))?
519
+ }
520
+
521
+ hoursSince(that: Date): Float {
522
+ let duration = self.jsValue->since(that.jsValue)
523
+ duration->total(Js->(unit = "hours", relativeTo = that.jsValue))?
524
+ }
525
+
526
+ minutesSince(that: Date): Float {
527
+ let duration = self.jsValue->since(that.jsValue)
528
+ duration->total(Js->(unit = "minutes", relativeTo = that.jsValue))?
529
+ }
530
+
531
+ secondsSince(that: Date): Float {
532
+ let duration = self.jsValue->since(that.jsValue)
533
+ duration->total(Js->(unit = "seconds", relativeTo = that.jsValue))?
534
+ }
535
+
536
+ millisecondsSince(that: Date): Float {
537
+ let duration = self.jsValue->since(that.jsValue)
538
+ duration->total(Js->(unit = "milliseconds", relativeTo = that.jsValue))?
539
+ }
540
+
541
+ microsecondsSince(that: Date): Float {
542
+ let duration = self.jsValue->since(that.jsValue)
543
+ duration->total(Js->(unit = "microseconds", relativeTo = that.jsValue))?
544
+ }
545
+
546
+ nanosecondsSince(that: Date): Float {
547
+ let duration = self.jsValue->since(that.jsValue)
548
+ duration->total(Js->(unit = "nanoseconds", relativeTo = that.jsValue))?
549
+ }
550
+
551
+ schedule(nextDate: Date => Date): Stream[Date] {
552
+ mutable current = self
553
+ [self].toStream().addAll(Stream.new {
554
+ current = nextDate(current)
555
+ Some(current)
556
+ })
557
+ }
558
+
559
+ }
560
+
561
+ extend self: DateGap {
562
+
563
+ toIso8601(
564
+ smallestUnit: Option[String] = None
565
+ fractionalSecondDigits: Option[Int] = None
566
+ ): String {
567
+ let duration = Js->Temporal->Duration->from(Js->(
568
+ years = self.years
569
+ months = self.months
570
+ weeks = self.weeks
571
+ days = self.days
572
+ hours = self.hours
573
+ minutes = self.minutes
574
+ seconds = self.seconds
575
+ milliseconds = self.milliseconds
576
+ microseconds = self.microseconds
577
+ nanoseconds = self.nanoseconds
578
+ ))
579
+ duration->toString(Js->(
580
+ smallestUnit = smallestUnit.map {_!}.else {Js.undefined()}
581
+ fractionalSecondDigits = fractionalSecondDigits.map {_!}.else {"auto"!}
582
+ ))?
583
+ }
584
+
585
+ }
586
+
587
+ utcTimeZoneId: String = "UTC"
588
+ isoCalendarId: String = "iso8601"
589
+
590
+ monday: Int = 1
591
+ tuesday: Int = 2
592
+ wednesday: Int = 3
593
+ thursday: Int = 4
594
+ friday: Int = 5
595
+ saturday: Int = 6
596
+ sunday: Int = 7
597
+
598
+ january: Int = 1
599
+ february: Int = 2
600
+ march: Int = 3
601
+ april: Int = 4
602
+ may: Int = 5
603
+ june: Int = 6
604
+ july: Int = 7
605
+ august: Int = 8
606
+ september: Int = 9
607
+ october: Int = 10
608
+ november: Int = 11
609
+ december: Int = 12
610
+
611
+ internalDisambiguation(earlier: Bool, later: Bool): JsValue {
612
+ Js->(
613
+ disambiguation = if(earlier && later) {
614
+ "compatible"
615
+ } elseIf {earlier} {
616
+ "earlier"
617
+ } elseIf {later} {
618
+ "later"
619
+ } else {
620
+ "reject"
621
+ }
622
+ )
623
+ }
package/core/Instant.ff CHANGED
@@ -1,24 +0,0 @@
1
- newtype Instant(since1970: Duration)
2
-
3
- fromIso(date: String): Option[Instant] {
4
- let zone = date.endsWith("Z") || date.contains("+") || date.dropWhile {_ != 'T'}.contains("-")
5
- if(zone && date.takeWhile {_ != 'T'}.contains("-") && date.contains("T") && date.contains(":")) {
6
- internalParseDate(date)
7
- }
8
- }
9
-
10
- extend self: Instant {
11
-
12
- add(duration: Duration): Instant {
13
- Instant(Duration(self.since1970.seconds + duration.seconds))
14
- }
15
-
16
- toIso(): String {
17
- Js->Date->(self.since1970.seconds * 1000.0)->toISOString()?
18
- }
19
-
20
- }
21
-
22
- internalParseDate(date: String): Instant {
23
- Instant(Duration(Js->Date->parse(date)? * 0.001))
24
- }
package/core/JsValue.ff CHANGED
@@ -400,7 +400,7 @@ instance List[T: IsJsValue]: IsJsValue {}
400
400
  instance IntMap[T: IsJsValue]: IsJsValue {}
401
401
  instance StringMap[T: IsJsValue]: IsJsValue {}
402
402
  instance Error: IsJsValue {}
403
- instance Instant: IsJsValue {}
403
+ instance Date: IsJsValue {}
404
404
  instance Duration: IsJsValue {}
405
405
  instance Buffer: IsJsValue {}
406
406
  instance Nothing: IsJsValue {}
package/core/Map.ff CHANGED
@@ -30,6 +30,14 @@ extend self[K: Order, V]: Map[K, V] {
30
30
  self.redBlack.get(key)
31
31
  }
32
32
 
33
+ first(): Option[Pair[K, V]] {
34
+ self.redBlack.first()
35
+ }
36
+
37
+ last(): Option[Pair[K, V]] {
38
+ self.redBlack.last()
39
+ }
40
+
33
41
  lastBefore(key: K): Option[Pair[K, V]] {
34
42
  self.redBlack.lastBefore(key)
35
43
  }
@@ -54,6 +54,11 @@ extend self: NodeSystem {
54
54
  Js.jsSystem()
55
55
  }
56
56
 
57
+ date(timeZoneId: Option[String] = None, calendarId: String = Date.isoCalendarId): Date {
58
+ let date = Date(Js->Temporal->Now->zonedDateTimeISO(timeZoneId.map {_!}.else {Js.undefined()}))
59
+ if(calendarId == Date.isoCalendarId) {date} else {date.withCalendar(calendarId)}
60
+ }
61
+
57
62
  exit[T](exitCode: Int = 0): T {
58
63
  Js->process->exit(exitCode)?
59
64
  }