tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

helper-telemetry.js (3787B)


      1 /* Any copyright is dedicated to the Public Domain.
      2   http://creativecommons.org/publicdomain/zero/1.0/ */
      3 
      4 "use strict";
      5 
      6 /* import-globals-from head.js */
      7 
      8 /**
      9 * Reset all telemetry events.
     10 */
     11 function setupTelemetryTest() {
     12  // Let's reset the counts.
     13  Services.telemetry.clearEvents();
     14 
     15  // Ensure no events have been logged
     16  const ALL_CHANNELS = Ci.nsITelemetry.DATASET_ALL_CHANNELS;
     17  const snapshot = Services.telemetry.snapshotEvents(ALL_CHANNELS, true);
     18  ok(!snapshot.parent, "No events have been logged for the main process");
     19 }
     20 /* exported setupTelemetryTest */
     21 
     22 /**
     23 * Check that the logged telemetry events exactly match the array of expected events.
     24 * Will compare the number of events, the event methods, and the event extras including
     25 * the about:debugging session id.
     26 */
     27 function checkTelemetryEvents(expectedEvents, expectedSessionId) {
     28  const evts = readAboutDebuggingEvents();
     29  is(evts.length, expectedEvents.length, "Expected number of events");
     30  if (evts.length !== expectedEvents.length) {
     31    info("Expected:" + JSON.stringify(expectedEvents, null, 2));
     32    info("Got: " + JSON.stringify(evts, null, 2));
     33  }
     34 
     35  function _eventHasExpectedExtras(e, expectedEvent) {
     36    const expectedExtras = Object.keys(expectedEvent.extras);
     37    return expectedExtras.every(extra => {
     38      return e.extras[extra] === expectedEvent.extras[extra];
     39    });
     40  }
     41 
     42  for (const expectedEvent of expectedEvents) {
     43    const sameMethodEvents = evts.filter(
     44      e => e.method === expectedEvent.method
     45    );
     46    ok(
     47      !!sameMethodEvents.length,
     48      "Found event for method: " + expectedEvent.method
     49    );
     50 
     51    const sameExtrasEvents = sameMethodEvents.filter(e =>
     52      _eventHasExpectedExtras(e, expectedEvent)
     53    );
     54    Assert.strictEqual(
     55      sameExtrasEvents.length,
     56      1,
     57      "Found exactly one event matching the expected extras"
     58    );
     59    if (sameExtrasEvents.length === 0) {
     60      info(JSON.stringify(sameMethodEvents));
     61    }
     62    is(
     63      sameExtrasEvents[0].extras.session_id,
     64      expectedSessionId,
     65      "Select page event has the expected session"
     66    );
     67  }
     68 
     69  return evts;
     70 }
     71 /* exported checkTelemetryEvents */
     72 
     73 /**
     74 * Retrieve the session id from an "open" event.
     75 * Note that calling this will "clear" all the events.
     76 */
     77 function getOpenEventSessionId() {
     78  const openEvents = readAboutDebuggingEvents().filter(
     79    e => e.method === "open_adbg"
     80  );
     81  ok(!!openEvents[0], "Found an about:debugging open event");
     82  return openEvents[0].extras.session_id;
     83 }
     84 /* exported getOpenEventSessionId */
     85 
     86 /**
     87 * Read all the pending events that have "aboutdebugging" as their object property.
     88 * WARNING: Calling this method also flushes/clears the events.
     89 */
     90 function readAboutDebuggingEvents() {
     91  const ALL_CHANNELS = Ci.nsITelemetry.DATASET_ALL_CHANNELS;
     92  // Retrieve and clear telemetry events.
     93  const snapshot = Services.telemetry.snapshotEvents(ALL_CHANNELS, true);
     94  // about:debugging events are logged in the parent process
     95  const parentEvents = snapshot.parent || [];
     96 
     97  return parentEvents
     98    .map(_toEventObject)
     99    .filter(e => e.object === "aboutdebugging");
    100 }
    101 /* exported getLoggedEvents */
    102 
    103 /**
    104 * The telemetry event data structure is simply an array. This helper remaps the array to
    105 * an object with more user friendly properties.
    106 */
    107 function _toEventObject(rawEvent) {
    108  return {
    109    // Category is typically devtools.main for us.
    110    category: rawEvent[1],
    111    // Method is the event's name (eg open, select_page etc...)
    112    method: rawEvent[2],
    113    // Object will usually be aboutdebugging for our tests
    114    object: rawEvent[3],
    115    // Value is usually empty for devtools events
    116    value: rawEvent[4],
    117    // Extras contain all the details of the event, including the session_id.
    118    extras: rawEvent[5],
    119  };
    120 }