Procházet zdrojové kódy

LibJS: Add Temporal.Instant.compare()

Idan Horowitz před 4 roky
rodič
revize
33cf6274e8

+ 1 - 0
Userland/Libraries/LibJS/Runtime/CommonPropertyNames.h

@@ -92,6 +92,7 @@ namespace JS {
     P(console)                               \
     P(construct)                             \
     P(constructor)                           \
+    P(compare)                               \
     P(copyWithin)                            \
     P(cos)                                   \
     P(cosh)                                  \

+ 15 - 0
Userland/Libraries/LibJS/Runtime/Temporal/Instant.cpp

@@ -138,4 +138,19 @@ BigInt* parse_temporal_instant(GlobalObject& global_object, String const& iso_st
     return js_bigint(vm.heap(), utc->big_integer().minus(Crypto::SignedBigInteger::create_from(offset_nanoseconds)));
 }
 
+// 8.5.5 CompareEpochNanoseconds ( epochNanosecondsOne, epochNanosecondsTwo )
+i32 compare_epoch_nanoseconds(BigInt const& epoch_nanoseconds_one, BigInt const& epoch_nanoseconds_two)
+{
+    // 1. If epochNanosecondsOne > epochNanosecondsTwo, return 1.
+    if (epoch_nanoseconds_one.big_integer() > epoch_nanoseconds_two.big_integer())
+        return 1;
+
+    // 2. If epochNanosecondsOne < epochNanosecondsTwo, return -1.
+    if (epoch_nanoseconds_one.big_integer() < epoch_nanoseconds_two.big_integer())
+        return -1;
+
+    // 3. Return 0.
+    return 0;
+}
+
 }

+ 1 - 0
Userland/Libraries/LibJS/Runtime/Temporal/Instant.h

@@ -40,5 +40,6 @@ bool is_valid_epoch_nanoseconds(BigInt const& epoch_nanoseconds);
 Instant* create_temporal_instant(GlobalObject&, BigInt& nanoseconds, FunctionObject* new_target = nullptr);
 Instant* to_temporal_instant(GlobalObject&, Value item);
 BigInt* parse_temporal_instant(GlobalObject&, String const& iso_string);
+i32 compare_epoch_nanoseconds(BigInt const&, BigInt const&);
 
 }

+ 18 - 0
Userland/Libraries/LibJS/Runtime/Temporal/InstantConstructor.cpp

@@ -31,6 +31,7 @@ void InstantConstructor::initialize(GlobalObject& global_object)
     define_native_function(vm.names.fromEpochMilliseconds, from_epoch_milliseconds, 1, attr);
     define_native_function(vm.names.fromEpochMicroseconds, from_epoch_microseconds, 1, attr);
     define_native_function(vm.names.fromEpochNanoseconds, from_epoch_nanoseconds, 1, attr);
+    define_native_function(vm.names.compare, compare, 2, attr);
 
     define_direct_property(vm.names.length, Value(1), Attribute::Configurable);
 }
@@ -158,4 +159,21 @@ JS_DEFINE_NATIVE_FUNCTION(InstantConstructor::from_epoch_nanoseconds)
     return create_temporal_instant(global_object, *epoch_nanoseconds);
 }
 
+// 8.2.7 Temporal.Instant.compare ( one, two ), https://tc39.es/proposal-temporal/#sec-temporal.instant.compare
+JS_DEFINE_NATIVE_FUNCTION(InstantConstructor::compare)
+{
+    // 1. Set one to ? ToTemporalInstant(one).
+    auto* one = to_temporal_instant(global_object, vm.argument(0));
+    if (vm.exception())
+        return {};
+
+    // 2. Set two to ? ToTemporalInstant(two).
+    auto* two = to_temporal_instant(global_object, vm.argument(1));
+    if (vm.exception())
+        return {};
+
+    // 3. Return 𝔽(! CompareEpochNanoseconds(one.[[Nanoseconds]], two.[[Nanoseconds]])).
+    return Value(compare_epoch_nanoseconds(one->nanoseconds(), two->nanoseconds()));
+}
+
 }

+ 1 - 0
Userland/Libraries/LibJS/Runtime/Temporal/InstantConstructor.h

@@ -28,6 +28,7 @@ private:
     JS_DECLARE_NATIVE_FUNCTION(from_epoch_milliseconds);
     JS_DECLARE_NATIVE_FUNCTION(from_epoch_microseconds);
     JS_DECLARE_NATIVE_FUNCTION(from_epoch_nanoseconds);
+    JS_DECLARE_NATIVE_FUNCTION(compare);
 };
 
 }

+ 13 - 0
Userland/Libraries/LibJS/Tests/builtins/Temporal/Instant/Instant.compare.js

@@ -0,0 +1,13 @@
+describe("correct behavior", () => {
+    test("length is 1", () => {
+        expect(Temporal.Instant.compare).toHaveLength(2);
+    });
+
+    test("basic functionality", () => {
+        const instant1 = new Temporal.Instant(111n);
+        expect(Temporal.Instant.compare(instant1, instant1)).toBe(0);
+        const instant2 = new Temporal.Instant(999n);
+        expect(Temporal.Instant.compare(instant1, instant2)).toBe(-1);
+        expect(Temporal.Instant.compare(instant2, instant1)).toBe(1);
+    });
+});