summaryrefslogtreecommitdiffstats
path: root/devtools/server/tests/xpcshell/test_nesting-02.js
blob: 27ff17fb988d7bbe7b080e7abe5c52138d325a59 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
/* Any copyright is dedicated to the Public Domain.
   http://creativecommons.org/publicdomain/zero/1.0/ */

"use strict";

// Test that we can nest event loops and then automatically exit nested event
// loops when requested.

add_task(
  threadFrontTest(async ({ threadFront, client }) => {
    // Reach over the protocol connection and get a reference to the thread actor.
    // TODO: rewrite the test so we don't do this..
    const thread = client._transport._serverConnection.getActor(
      threadFront.actorID
    );

    test_nesting(thread);
  })
);

function test_nesting(thread) {
  // The following things should happen (in order):
  // 1. In the new event loop (created by unsafeSynchronize)
  // 2. Resolve the promise (shouldn't exit any event loops)
  // 3. Exit the event loop (should also then exit unsafeSynchronize's event loop)
  // 4. Be after the unsafeSynchronize call
  let currentStep = 0;
  const p = new Promise(resolve => {
    executeSoon(function() {
      executeSoon(function() {
        // Should be at step 2
        Assert.equal(++currentStep, 2);
        // Before resolving, should have the unsafeSynchronize event loop and the
        // one just created.
        Assert.equal(thread._nestedEventLoops.size, 2);

        executeSoon(function() {
          // Should be at step 3
          Assert.equal(++currentStep, 3);
          // Before exiting the manually created event loop, should have the
          // unsafeSynchronize event loop and the manual event loop.
          Assert.equal(thread._nestedEventLoops.size, 2);
          // Should have the event loop
          Assert.ok(!!eventLoop);
          eventLoop.resolve();
        });

        resolve(true);
        // Shouldn't exit any event loops because a new one started since the call
        // to unsafeSynchronize
        Assert.equal(thread._nestedEventLoops.size, 2);
      });

      // Should be at step 1
      Assert.equal(++currentStep, 1);
      // Should have only the unsafeSynchronize event loop
      Assert.equal(thread._nestedEventLoops.size, 1);
      const eventLoop = thread._nestedEventLoops.push();
      eventLoop.enter();
    });
  });

  Assert.equal(thread.unsafeSynchronize(p), true);

  // Should be on the fourth step
  Assert.equal(++currentStep, 4);
  // There shouldn't be any nested event loops anymore
  Assert.equal(thread._nestedEventLoops.size, 0);
}