toolkit/devtools/server/tests/browser/browser_storage_dynamic_windows.js

Sat, 03 Jan 2015 20:18:00 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Sat, 03 Jan 2015 20:18:00 +0100
branch
TOR_BUG_3246
changeset 7
129ffea94266
permissions
-rw-r--r--

Conditionally enable double key logic according to:
private browsing mode or privacy.thirdparty.isolate preference and
implement in GetCookieStringCommon and FindCookie where it counts...
With some reservations of how to convince FindCookie users to test
condition and pass a nullptr when disabling double key logic.

     1 const Cu = Components.utils;
     2 Cu.import("resource://gre/modules/Services.jsm");
     3 let tempScope = {};
     4 Cu.import("resource://gre/modules/devtools/dbg-client.jsm", tempScope);
     5 Cu.import("resource://gre/modules/devtools/dbg-server.jsm", tempScope);
     6 Cu.import("resource://gre/modules/Promise.jsm", tempScope);
     7 let {DebuggerServer, DebuggerClient, Promise} = tempScope;
     8 tempScope = null;
    10 const {StorageFront} = require("devtools/server/actors/storage");
    11 let gFront, gWindow;
    13 const beforeReload = {
    14   cookies: {
    15     "test1.example.org": ["c1", "cs2", "c3", "uc1"],
    16     "sectest1.example.org": ["uc1", "cs2"]
    17   },
    18   localStorage: {
    19     "http://test1.example.org": ["ls1", "ls2"],
    20     "http://sectest1.example.org": ["iframe-u-ls1"]
    21   },
    22   sessionStorage: {
    23     "http://test1.example.org": ["ss1"],
    24     "http://sectest1.example.org": ["iframe-u-ss1", "iframe-u-ss2"]
    25   },
    26   indexedDB: {
    27     "http://test1.example.org": [
    28       JSON.stringify(["idb1", "obj1"]),
    29       JSON.stringify(["idb1", "obj2"]),
    30       JSON.stringify(["idb2", "obj3"]),
    31     ],
    32     "http://sectest1.example.org": []
    33   }
    34 };
    36 function finishTests(client) {
    37   // Cleanup so that indexed db created from this test do not interfere next ones
    39   /**
    40    * This method iterates over iframes in a window and clears the indexed db
    41    * created by this test.
    42    */
    43   let clearIDB = (w, i, c) => {
    44     if (w[i] && w[i].clear) {
    45       w[i].clearIterator = w[i].clear(() => clearIDB(w, i + 1, c));
    46       w[i].clearIterator.next();
    47     }
    48     else if (w[i] && w[i + 1]) {
    49       clearIDB(w, i + 1, c);
    50     }
    51     else {
    52       c();
    53     }
    54   };
    56   let closeConnection = () => {
    57     // Forcing GC/CC to get rid of docshells and windows created by this test.
    58     forceCollections();
    59     client.close(() => {
    60       forceCollections();
    61       DebuggerServer.destroy();
    62       forceCollections();
    63       gFront = gWindow = DebuggerClient = DebuggerServer = null;
    64       finish();
    65     });
    66   }
    67   gWindow.clearIterator = gWindow.clear(() => {
    68     clearIDB(gWindow, 0, closeConnection);
    69   });
    70   gWindow.clearIterator.next();
    71 }
    73 function testStores(data, client) {
    74   testWindowsBeforeReload(data);
    75   testReload().then(() =>
    76   testAddIframe()).then(() =>
    77   testRemoveIframe()).then(() =>
    78   finishTests(client));
    79 }
    81 function testWindowsBeforeReload(data) {
    82   for (let storageType in beforeReload) {
    83     ok(data[storageType], storageType + " storage actor is present");
    84     is(Object.keys(data[storageType].hosts).length,
    85        Object.keys(beforeReload[storageType]).length,
    86        "Number of hosts for " + storageType + "match");
    87     for (let host in beforeReload[storageType]) {
    88       ok(data[storageType].hosts[host], "Host " + host + " is present");
    89     }
    90   }
    91 }
    93 function markOutMatched(toBeEmptied, data, deleted) {
    94   if (!Object.keys(toBeEmptied).length) {
    95     info("Object empty")
    96     return;
    97   }
    98   ok(Object.keys(data).length,
    99      "Atleast some storage types should be present in deleted");
   100   for (let storageType in toBeEmptied) {
   101     if (!data[storageType]) {
   102       continue;
   103     }
   104     info("Testing for " + storageType);
   105     for (let host in data[storageType]) {
   106       ok(toBeEmptied[storageType][host], "Host " + host + " found");
   107       if (!deleted) {
   108         for (let item of data[storageType][host]) {
   109           let index = toBeEmptied[storageType][host].indexOf(item);
   110           ok(index > -1, "Item found - " + item);
   111           if (index > -1) {
   112             toBeEmptied[storageType][host].splice(index, 1);
   113           }
   114         }
   115         if (!toBeEmptied[storageType][host].length) {
   116           delete toBeEmptied[storageType][host];
   117         }
   118       }
   119       else {
   120         delete toBeEmptied[storageType][host];
   121       }
   122     }
   123     if (!Object.keys(toBeEmptied[storageType]).length) {
   124       delete toBeEmptied[storageType];
   125     }
   126   }
   127 }
   129 function testReload() {
   130   info("Testing if reload works properly");
   132   let shouldBeEmptyFirst = Cu.cloneInto(beforeReload,  {});
   133   let shouldBeEmptyLast = Cu.cloneInto(beforeReload,  {});
   134   let reloaded = Promise.defer();
   136   let onStoresUpdate = data => {
   137     info("in stores update of testReload");
   138     // This might be second time stores update is happening, in which case,
   139     // data.deleted will be null.
   140     // OR.. This might be the first time on a super slow machine where both
   141     // data.deleted and data.added is missing in the first update.
   142     if (data.deleted) {
   143       markOutMatched(shouldBeEmptyFirst, data.deleted, true);
   144     }
   146     if (!Object.keys(shouldBeEmptyFirst).length) {
   147       info("shouldBeEmptyFirst is empty now");
   148     }
   150     // stores-update call might not have data.added for the first time on slow
   151     // machines, in which case, data.added will be null
   152     if (data.added) {
   153       markOutMatched(shouldBeEmptyLast, data.added);
   154     }
   156     if (!Object.keys(shouldBeEmptyLast).length) {
   157       info("Everything to be received is received.");
   158       endTestReloaded();
   159     }
   160   };
   162   let endTestReloaded = () => {
   163     gFront.off("stores-update", onStoresUpdate);
   164     reloaded.resolve();
   165   };
   167   gFront.on("stores-update", onStoresUpdate);
   169   content.location.reload();
   170   return reloaded.promise;
   171 }
   173 function testAddIframe() {
   174   info("Testing if new iframe addition works properly");
   175   let reloaded = Promise.defer();
   177   let shouldBeEmpty = {
   178     localStorage: {
   179       "https://sectest1.example.org": ["iframe-s-ls1"]
   180     },
   181     sessionStorage: {
   182       "https://sectest1.example.org": ["iframe-s-ss1"]
   183     },
   184     cookies: {
   185       "sectest1.example.org": ["sc1"]
   186     },
   187     indexedDB: {
   188       // empty because indexed db creation happens after the page load, so at
   189       // the time of window-ready, there was no indexed db present.
   190       "https://sectest1.example.org": []
   191     }
   192   };
   194   let onStoresUpdate = data => {
   195     info("checking if the hosts list is correct for this iframe addition");
   197     markOutMatched(shouldBeEmpty, data.added);
   199     ok(!data.changed || !data.changed.cookies ||
   200        !data.changed.cookies["https://sectest1.example.org"],
   201        "Nothing got changed for cookies");
   202     ok(!data.changed || !data.changed.localStorage ||
   203        !data.changed.localStorage["https://sectest1.example.org"],
   204        "Nothing got changed for local storage");
   205     ok(!data.changed || !data.changed.sessionStorage ||
   206        !data.changed.sessionStorage["https://sectest1.example.org"],
   207        "Nothing got changed for session storage");
   208     ok(!data.changed || !data.changed.indexedDB ||
   209        !data.changed.indexedDB["https://sectest1.example.org"],
   210        "Nothing got changed for indexed db");
   212     ok(!data.deleted || !data.deleted.cookies ||
   213        !data.deleted.cookies["https://sectest1.example.org"],
   214        "Nothing got deleted for cookies");
   215     ok(!data.deleted || !data.deleted.localStorage ||
   216        !data.deleted.localStorage["https://sectest1.example.org"],
   217        "Nothing got deleted for local storage");
   218     ok(!data.deleted || !data.deleted.sessionStorage ||
   219        !data.deleted.sessionStorage["https://sectest1.example.org"],
   220        "Nothing got deleted for session storage");
   221     ok(!data.deleted || !data.deleted.indexedDB ||
   222        !data.deleted.indexedDB["https://sectest1.example.org"],
   223        "Nothing got deleted for indexed db");
   225     if (!Object.keys(shouldBeEmpty).length) {
   226       info("Everything to be received is received.");
   227       endTestReloaded();
   228     }
   229   };
   231   let endTestReloaded = () => {
   232     gFront.off("stores-update", onStoresUpdate);
   233     reloaded.resolve();
   234   };
   236   gFront.on("stores-update", onStoresUpdate);
   238   let iframe = content.document.createElement("iframe");
   239   iframe.src = ALT_DOMAIN_SECURED + "storage-secured-iframe.html";
   240   content.document.querySelector("body").appendChild(iframe);
   241   return reloaded.promise;
   242 }
   244 function testRemoveIframe() {
   245   info("Testing if iframe removal works properly");
   246   let reloaded = Promise.defer();
   248   let shouldBeEmpty = {
   249     localStorage: {
   250       "http://sectest1.example.org": []
   251     },
   252     sessionStorage: {
   253       "http://sectest1.example.org": []
   254     }
   255   };
   257   let onStoresUpdate = data => {
   258     info("checking if the hosts list is correct for this iframe deletion");
   260     markOutMatched(shouldBeEmpty, data.deleted, true);
   262     ok(!data.deleted.cookies || !data.deleted.cookies["sectest1.example.org"],
   263        "Nothing got deleted for Cookies as the same hostname is still present");
   265     ok(!data.changed || !data.changed.cookies ||
   266        !data.changed.cookies["http://sectest1.example.org"],
   267        "Nothing got changed for cookies");
   268     ok(!data.changed || !data.changed.localStorage ||
   269        !data.changed.localStorage["http://sectest1.example.org"],
   270        "Nothing got changed for local storage");
   271     ok(!data.changed || !data.changed.sessionStorage ||
   272        !data.changed.sessionStorage["http://sectest1.example.org"],
   273        "Nothing got changed for session storage");
   275     ok(!data.added || !data.added.cookies ||
   276        !data.added.cookies["http://sectest1.example.org"],
   277        "Nothing got added for cookies");
   278     ok(!data.added || !data.added.localStorage ||
   279        !data.added.localStorage["http://sectest1.example.org"],
   280        "Nothing got added for local storage");
   281     ok(!data.added || !data.added.sessionStorage ||
   282        !data.added.sessionStorage["http://sectest1.example.org"],
   283        "Nothing got added for session storage");
   285     if (!Object.keys(shouldBeEmpty).length) {
   286       info("Everything to be received is received.");
   287       endTestReloaded();
   288     }
   289   };
   291   let endTestReloaded = () => {
   292     gFront.off("stores-update", onStoresUpdate);
   293     reloaded.resolve();
   294   };
   296   gFront.on("stores-update", onStoresUpdate);
   298   for (let iframe of content.document.querySelectorAll("iframe")) {
   299     if (iframe.src.startsWith("http:")) {
   300       iframe.remove();
   301       break;
   302     }
   303   }
   304   return reloaded.promise;
   305 }
   307 function test() {
   308   waitForExplicitFinish();
   309   addTab(MAIN_DOMAIN + "storage-dynamic-windows.html", function(doc) {
   310     try {
   311       // Sometimes debugger server does not get destroyed correctly by previous
   312       // tests.
   313       DebuggerServer.destroy();
   314     } catch (ex) { }
   315     DebuggerServer.init(function () { return true; });
   316     DebuggerServer.addBrowserActors();
   318     let createConnection = () => {
   319       let client = new DebuggerClient(DebuggerServer.connectPipe());
   320       client.connect(function onConnect() {
   321         client.listTabs(function onListTabs(aResponse) {
   322           let form = aResponse.tabs[aResponse.selected];
   323           gFront = StorageFront(client, form);
   325           gFront.listStores().then(data => testStores(data, client));
   326         });
   327       });
   328     };
   330     /**
   331      * This method iterates over iframes in a window and setups the indexed db
   332      * required for this test.
   333      */
   334     let setupIDBInFrames = (w, i, c) => {
   335       if (w[i] && w[i].idbGenerator) {
   336         w[i].setupIDB = w[i].idbGenerator(() => setupIDBInFrames(w, i + 1, c));
   337         w[i].setupIDB.next();
   338       }
   339       else if (w[i] && w[i + 1]) {
   340         setupIDBInFrames(w, i + 1, c);
   341       }
   342       else {
   343         c();
   344       }
   345     };
   346     // Setup the indexed db in main window.
   347     gWindow = doc.defaultView.wrappedJSObject;
   348     gWindow.setupIDB = gWindow.idbGenerator(() => {
   349       setupIDBInFrames(gWindow, 0, createConnection);
   350     });
   351     gWindow.setupIDB.next();
   352   });
   353 }

mercurial