| // META: global=window,worker |
| |
| test((t) => { |
| const signal = TaskSignal.any([]); |
| assert_true(signal instanceof TaskSignal); |
| assert_equals(signal.priority, 'user-visible'); |
| }, "TaskSignal.any() returns a user-visible TaskSignal when no priority is specified"); |
| |
| test((t) => { |
| let signal = TaskSignal.any([], {priority: 'user-blocking'}); |
| assert_equals(signal.priority, 'user-blocking'); |
| |
| signal = TaskSignal.any([], {priority: 'user-visible'}); |
| assert_equals(signal.priority, 'user-visible'); |
| |
| signal = TaskSignal.any([], {priority: 'background'}); |
| assert_equals(signal.priority, 'background'); |
| }, "TaskSignal.any() returns a signal with the correct priority when intialized with a string"); |
| |
| test((t) => { |
| let controller = new TaskController({priority: 'user-blocking'}); |
| let signal = TaskSignal.any([], {priority: controller.signal}); |
| assert_equals(signal.priority, 'user-blocking'); |
| |
| controller = new TaskController({priority: 'user-visible'}); |
| signal = TaskSignal.any([], {priority: controller.signal}); |
| assert_equals(signal.priority, 'user-visible'); |
| |
| controller = new TaskController({priority: 'background'}); |
| signal = TaskSignal.any([], {priority: controller.signal}); |
| assert_equals(signal.priority, 'background'); |
| }, "TaskSignal.any() returns a signal with the correct priority when intialized with a TaskSignal"); |
| |
| test((t) => { |
| let controller = new TaskController({priority: 'user-blocking'}); |
| let signal = TaskSignal.any([], {priority: controller.signal}); |
| assert_equals(signal.priority, 'user-blocking'); |
| |
| controller.setPriority('user-visible'); |
| assert_equals(signal.priority, 'user-visible'); |
| |
| controller.setPriority('background'); |
| assert_equals(signal.priority, 'background'); |
| |
| controller.setPriority('user-blocking'); |
| assert_equals(signal.priority, 'user-blocking'); |
| }, "TaskSignal.any() returns a signal with dynamic priority"); |
| |
| test((t) => { |
| const controller = new TaskController(); |
| const signal = TaskSignal.any([], {priority: controller.signal}); |
| |
| let eventFiredCount = 0; |
| signal.onprioritychange = t.step_func((e) => { |
| assert_equals(e.target, signal, |
| `The event target is the signal returned by TaskSignal.any()`); |
| ++eventFiredCount; |
| }); |
| |
| controller.setPriority('background'); |
| assert_equals(eventFiredCount, 1); |
| |
| controller.setPriority('user-visible'); |
| assert_equals(eventFiredCount, 2); |
| |
| controller.setPriority('user-blocking'); |
| assert_equals(eventFiredCount, 3); |
| }, "Priority change events fire for composite signals"); |
| |
| |
| test((t) => { |
| const controller = new TaskController(); |
| let signal = TaskSignal.any([], {priority: controller.signal}); |
| signal = TaskSignal.any([], {priority: signal}); |
| signal = TaskSignal.any([], {priority: signal}); |
| signal = TaskSignal.any([], {priority: signal}); |
| signal = TaskSignal.any([], {priority: signal}); |
| |
| assert_equals(signal.priority, 'user-visible'); |
| |
| let eventFiredCount = 0; |
| signal.onprioritychange = t.step_func((e) => { |
| assert_equals(e.target, signal, |
| "The event target is the signal returned by TaskSignal.any()"); |
| ++eventFiredCount; |
| }); |
| |
| controller.setPriority('background'); |
| assert_equals(eventFiredCount, 1); |
| assert_equals(signal.priority, 'background'); |
| |
| controller.setPriority('user-visible'); |
| assert_equals(eventFiredCount, 2); |
| assert_equals(signal.priority, 'user-visible'); |
| |
| controller.setPriority('user-blocking'); |
| assert_equals(eventFiredCount, 3); |
| assert_equals(signal.priority, 'user-blocking'); |
| }, "Priority change events fire for composite signals with intermediate sources"); |
| |
| test((t) => { |
| const controller = new TaskController(); |
| const signals = []; |
| const results = []; |
| |
| let id = 0; |
| for (let i = 0; i < 3; i++) { |
| const signal = TaskSignal.any([], {priority: controller.signal}); |
| const eventId = id++; |
| signal.addEventListener('prioritychange', () => { |
| results.push(eventId); |
| }); |
| signals.push(signal); |
| } |
| for (let i = 0; i < 3; i++) { |
| const signal = TaskSignal.any([], {priority: signals[i]}); |
| const eventId = id++; |
| signal.addEventListener('prioritychange', () => { |
| results.push(eventId); |
| }); |
| } |
| |
| controller.setPriority('background'); |
| assert_equals(results.toString(), '0,1,2,3,4,5') |
| |
| controller.setPriority('user-blocking'); |
| assert_equals(results.toString(), '0,1,2,3,4,5,0,1,2,3,4,5') |
| }, "Priority change propagates to multiple dependent signals in the right order"); |
| |
| test((t) => { |
| const controller = new TaskController(); |
| const signal = TaskSignal.any([], {priority: controller.signal}); |
| |
| let fired = false; |
| signal.onabort = t.step_func(() => { |
| assert_unreached("The signal should not abort"); |
| fired = true; |
| }); |
| |
| controller.abort(); |
| assert_false(fired); |
| }, "TaskSignal.any() does not propagate abort when not given dependent abort signals"); |
| |
| test((t) => { |
| const taskController = new TaskController(); |
| const abortController = new AbortController(); |
| const signal = TaskSignal.any([abortController.signal], {priority: taskController.signal}); |
| |
| let priorityFireCount = 0; |
| signal.onprioritychange = t.step_func(() => { |
| ++priorityFireCount; |
| }); |
| |
| let abortFired = false; |
| signal.onabort = t.step_func(() => { |
| abortFired = true; |
| }); |
| |
| taskController.setPriority('background'); |
| assert_equals(signal.priority, 'background'); |
| assert_equals(priorityFireCount, 1); |
| |
| taskController.abort(); |
| assert_false(abortFired, "The signal should use abortController for abort"); |
| |
| abortController.abort(); |
| assert_true(abortFired); |
| |
| taskController.setPriority('user-visible'); |
| assert_equals(signal.priority, 'user-visible'); |
| assert_equals(priorityFireCount, 2); |
| }, "TaskSignal.any() propagates abort and priority"); |
| |
| |
| test((t) => { |
| const controller = new TaskController(); |
| const signal = TaskSignal.any([AbortSignal.abort()], {priority: controller.signal}); |
| |
| let fired = false; |
| signal.onprioritychange = t.step_func(() => { |
| fired = true; |
| }); |
| |
| controller.setPriority('background'); |
| assert_true(fired); |
| }, "TaskSignal.any() propagates priority after returning an aborted signal"); |
| |
| test((t) => { |
| // Add a dependent in the initial event dispatch stage. |
| let controller = new TaskController(); |
| let fired = false; |
| controller.signal.onprioritychange = t.step_func(() => { |
| fired = true; |
| const newSignal = TaskSignal.any([], {priority: controller.signal}); |
| assert_equals(newSignal.priority, 'background'); |
| newSignal.onprioritychange = t.unreached_func('onprioritychange called'); |
| }); |
| controller.setPriority('background'); |
| assert_true(fired); |
| |
| // Add a dependent while signaling prioritychange on dependents. |
| fired = false; |
| controller = new TaskController(); |
| const signal = TaskSignal.any([], {priority: controller.signal}); |
| signal.onprioritychange = t.step_func(() => { |
| fired = true; |
| const newSignal = TaskSignal.any([], {priority: signal}); |
| assert_equals(newSignal.priority, 'background'); |
| newSignal.onprioritychange = t.unreached_func('onprioritychange called'); |
| }); |
| controller.setPriority('background'); |
| assert_true(fired); |
| }, "TaskSignal.any() does not fire prioritychange for dependents added during prioritychange"); |