@@ -513,11 +513,15 @@ impl ScriptRuntime {
513513 base_url : base_url. cloned ( ) ,
514514 modules : RefCell :: new ( HashMap :: new ( ) ) ,
515515 } ) ;
516+ let ctx = DomCtx :: new ( doc) ;
517+ // Share the runtime's clock with boa so that `Date` observes the same
518+ // (possibly virtual) time as timers
519+ let clock = ctx. state . borrow ( ) . clock . clone ( ) ;
516520 let mut context = Context :: builder ( )
517521 . module_loader ( module_loader. clone ( ) )
522+ . clock ( Rc :: new ( crate :: clock:: BoaClockAdapter :: new ( clock) ) )
518523 . build ( )
519524 . expect ( "failed to build JS context" ) ;
520- let ctx = DomCtx :: new ( doc) ;
521525 context. insert_data ( ctx. clone ( ) ) ;
522526
523527 Console :: register_with_logger ( LogCrateLogger , & mut context)
@@ -812,7 +816,11 @@ impl ScriptRuntime {
812816
813817 /// Run all timers that are currently due. Returns `true` if any JavaScript was run.
814818 pub fn run_due_timers ( & mut self ) -> bool {
815- let due = self . ctx . state . borrow_mut ( ) . timers . take_due ( Instant :: now ( ) ) ;
819+ let due = {
820+ let mut state = self . ctx . state . borrow_mut ( ) ;
821+ let now = state. clock . now ( ) ;
822+ state. timers . take_due ( now)
823+ } ;
816824 if due. is_empty ( ) {
817825 return false ;
818826 }
@@ -1262,11 +1270,9 @@ fn set_timeout(_: &JsValue, args: &[JsValue], context: &mut Context) -> JsResult
12621270 let Some ( ( callback, delay, rest) ) = timer_args ( args, context) ? else {
12631271 return Ok ( JsValue :: from ( 0 ) ) ;
12641272 } ;
1265- let id = ctx
1266- . state
1267- . borrow_mut ( )
1268- . timers
1269- . add ( delay, None , callback, rest) ;
1273+ let mut state = ctx. state . borrow_mut ( ) ;
1274+ let now = state. clock . now ( ) ;
1275+ let id = state. timers . add ( now, delay, None , callback, rest) ;
12701276 Ok ( JsValue :: from ( id as f64 ) )
12711277}
12721278
@@ -1275,11 +1281,9 @@ fn set_interval(_: &JsValue, args: &[JsValue], context: &mut Context) -> JsResul
12751281 let Some ( ( callback, delay, rest) ) = timer_args ( args, context) ? else {
12761282 return Ok ( JsValue :: from ( 0 ) ) ;
12771283 } ;
1278- let id = ctx
1279- . state
1280- . borrow_mut ( )
1281- . timers
1282- . add ( delay, Some ( delay) , callback, rest) ;
1284+ let mut state = ctx. state . borrow_mut ( ) ;
1285+ let now = state. clock . now ( ) ;
1286+ let id = state. timers . add ( now, delay, Some ( delay) , callback, rest) ;
12831287 Ok ( JsValue :: from ( id as f64 ) )
12841288}
12851289
@@ -1298,7 +1302,10 @@ fn request_animation_frame(
12981302 } ;
12991303 // Approximate the next frame as ~16ms away
13001304 let timestamp = JsValue :: from ( 16.0 ) ;
1301- let id = ctx. state . borrow_mut ( ) . timers . add (
1305+ let mut state = ctx. state . borrow_mut ( ) ;
1306+ let now = state. clock . now ( ) ;
1307+ let id = state. timers . add (
1308+ now,
13021309 Duration :: from_millis ( 16 ) ,
13031310 None ,
13041311 callback,
0 commit comments