Sat, 03 Jan 2015 20:18:00 +0100
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 /* This Source Code Form is subject to the terms of the Mozilla Public
2 * License, v. 2.0. If a copy of the MPL was not distributed with this
3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4 "use strict";
6 require("sdk/clipboard");
8 const { Cc, Ci } = require("chrome");
10 const imageTools = Cc["@mozilla.org/image/tools;1"].
11 getService(Ci.imgITools);
13 const io = Cc["@mozilla.org/network/io-service;1"].
14 getService(Ci.nsIIOService);
16 const base64png = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAYA" +
17 "AABzenr0AAAASUlEQVRYhe3O0QkAIAwD0eyqe3Q993AQ3cBSUKpygfsNTy" +
18 "N5ugbQpK0BAADgP0BRDWXWlwEAAAAAgPsA3rzDaAAAAHgPcGrpgAnzQ2FG" +
19 "bWRR9AAAAABJRU5ErkJggg%3D%3D";
21 const base64jpeg = "data:image/jpeg;base64,%2F9j%2F4AAQSkZJRgABAQAAAQABAAD%2F" +
22 "2wBDAAMCAgICAgMCAgIDAwMDBAYEBAQEBAgGBgUGCQgKCgkICQkKDA8MCg" +
23 "sOCwkJDRENDg8QEBEQCgwSExIQEw8QEBD%2F2wBDAQMDAwQDBAgEBAgQCw" +
24 "kLEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQEBAQ" +
25 "EBAQEBAQEBD%2FwAARCAAgACADAREAAhEBAxEB%2F8QAHwAAAQUBAQEBAQ" +
26 "EAAAAAAAAAAAECAwQFBgcICQoL%2F8QAtRAAAgEDAwIEAwUFBAQAAAF9AQ" +
27 "IDAAQRBRIhMUEGE1FhByJxFDKBkaEII0KxwRVS0fAkM2JyggkKFhcYGRol" +
28 "JicoKSo0NTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eX" +
29 "qDhIWGh4iJipKTlJWWl5iZmqKjpKWmp6ipqrKztLW2t7i5usLDxMXGx8jJ" +
30 "ytLT1NXW19jZ2uHi4%2BTl5ufo6erx8vP09fb3%2BPn6%2F8QAHwEAAwEB" +
31 "AQEBAQEBAQAAAAAAAAECAwQFBgcICQoL%2F8QAtREAAgECBAQDBAcFBAQA" +
32 "AQJ3AAECAxEEBSExBhJBUQdhcRMiMoEIFEKRobHBCSMzUvAVYnLRChYkNO" +
33 "El8RcYGRomJygpKjU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hpanN0" +
34 "dXZ3eHl6goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6ws" +
35 "PExcbHyMnK0tPU1dbX2Nna4uPk5ebn6Onq8vP09fb3%2BPn6%2F9oADAMB" +
36 "AAIRAxEAPwD5Kr8kP9CwoA5f4m%2F8iRqX%2FbH%2FANHJXr5F%2FwAjCn" +
37 "8%2F%2FSWfnnir%2FwAkji%2F%2B4f8A6dgeD1%2BiH8bn1BX5If6FmFqW" +
38 "pXtveyQwzbUXGBtB7D2r9l4U4UyjMsoo4rFUeacua75pLaUktFJLZH5NxN" +
39 "xNmmX5pVw2Gq8sI8tlyxe8U3q03uzD8S3dxqOi3NneSeZDJs3LgDOHBHI5" +
40 "6gV%2BkcG%2BH%2FDmJzuhSq4e8XzfbqfyS%2FvH5rx1xTm2MyDEUa1W8X" +
41 "yXXLFbTi%2BkThv7B0r%2FAJ9f%2FH2%2Fxr90%2FwCIVcI%2F9An%2FAJ" +
42 "Uq%2FwDyZ%2FO%2F16v%2FADfgv8j0r%2FhZvgj%2FAKDf%2FktN%2FwDE" +
43 "V%2Fnr%2FYWYf8%2B%2Fxj%2Fmf3R%2FxFXhH%2FoL%2FwDKdX%2F5Azrv" +
44 "xLouo3D3lne%2BZDJja3luM4GDwRnqDX9LeH%2FBud4nhzD1aVC8Xz%2Fa" +
45 "h%2Fz8l%2FePx%2FinjrIMZm1WtRxF4vls%2BSa2jFdYlDUdRsp7OSKKbc" +
46 "7YwNpHce1fqfCvCub5bm9HFYqjywjzXfNF7xklopN7s%2BC4l4lyvMMrq4" +
47 "fD1bzfLZcsltJPqktkYlfsZ%2BUnBV%2FnufVnXaD%2FAMgqD%2FgX%2Fo" +
48 "Rr%2BxvCr%2FkkcJ%2F3E%2F8ATsz5%2FHfx5fL8kX6%2FQjkCgD%2F%2F" +
49 "2Q%3D%3D";
51 const canvasHTML = "data:text/html," + encodeURIComponent(
52 "<html>\
53 <body>\
54 <canvas width='32' height='32'></canvas>\
55 </body>\
56 </html>"
57 );
59 function comparePixelImages(imageA, imageB, callback) {
60 let tabs = require("sdk/tabs");
62 tabs.open({
63 url: canvasHTML,
65 onReady: function onReady(tab) {
66 let worker = tab.attach({
67 contentScript: "new " + function() {
68 let canvas = document.querySelector("canvas");
69 let context = canvas.getContext("2d");
71 self.port.on("draw-image", function(imageURI) {
72 let img = new Image();
74 img.onload = function() {
75 context.drawImage(this, 0, 0);
77 let pixels = Array.join(context.getImageData(0, 0, 32, 32).data);
78 self.port.emit("image-pixels", pixels);
79 }
81 img.src = imageURI;
82 });
83 }
84 });
86 let compared = "";
88 worker.port.on("image-pixels", function (pixels) {
89 if (!compared) {
90 compared = pixels;
91 this.emit("draw-image", imageB);
92 } else {
93 callback(compared === pixels);
94 tab.close()
95 }
96 });
98 worker.port.emit("draw-image", imageA);
99 }
100 });
101 }
104 // Test the typical use case, setting & getting with no flavors specified
105 exports["test With No Flavor"] = function(assert) {
106 var contents = "hello there";
107 var flavor = "text";
108 var fullFlavor = "text/unicode";
109 var clip = require("sdk/clipboard");
111 // Confirm we set the clipboard
112 assert.ok(clip.set(contents));
114 // Confirm flavor is set
115 assert.equal(clip.currentFlavors[0], flavor);
117 // Confirm we set the clipboard
118 assert.equal(clip.get(), contents);
120 // Confirm we can get the clipboard using the flavor
121 assert.equal(clip.get(flavor), contents);
123 // Confirm we can still get the clipboard using the full flavor
124 assert.equal(clip.get(fullFlavor), contents);
125 };
127 // Test the slightly less common case where we specify the flavor
128 exports["test With Flavor"] = function(assert) {
129 var contents = "<b>hello there</b>";
130 var contentsText = "hello there";
131 var flavor = "html";
132 var fullFlavor = "text/html";
133 var unicodeFlavor = "text";
134 var unicodeFullFlavor = "text/unicode";
135 var clip = require("sdk/clipboard");
137 assert.ok(clip.set(contents, flavor));
139 assert.equal(clip.currentFlavors[0], unicodeFlavor);
140 assert.equal(clip.currentFlavors[1], flavor);
141 assert.equal(clip.get(), contentsText);
142 assert.equal(clip.get(flavor), contents);
143 assert.equal(clip.get(fullFlavor), contents);
144 assert.equal(clip.get(unicodeFlavor), contentsText);
145 assert.equal(clip.get(unicodeFullFlavor), contentsText);
146 };
148 // Test that the typical case still works when we specify the flavor to set
149 exports["test With Redundant Flavor"] = function(assert) {
150 var contents = "<b>hello there</b>";
151 var flavor = "text";
152 var fullFlavor = "text/unicode";
153 var clip = require("sdk/clipboard");
155 assert.ok(clip.set(contents, flavor));
156 assert.equal(clip.currentFlavors[0], flavor);
157 assert.equal(clip.get(), contents);
158 assert.equal(clip.get(flavor), contents);
159 assert.equal(clip.get(fullFlavor), contents);
160 };
162 exports["test Not In Flavor"] = function(assert) {
163 var contents = "hello there";
164 var flavor = "html";
165 var clip = require("sdk/clipboard");
167 assert.ok(clip.set(contents));
168 // If there's nothing on the clipboard with this flavor, should return null
169 assert.equal(clip.get(flavor), null);
170 };
172 exports["test Set Image"] = function(assert) {
173 var clip = require("sdk/clipboard");
174 var flavor = "image";
175 var fullFlavor = "image/png";
177 assert.ok(clip.set(base64png, flavor), "clipboard set");
178 assert.equal(clip.currentFlavors[0], flavor, "flavor is set");
179 };
181 exports["test Get Image"] = function(assert, done) {
182 var clip = require("sdk/clipboard");
184 clip.set(base64png, "image");
186 var contents = clip.get();
188 comparePixelImages(base64png, contents, function (areEquals) {
189 assert.ok(areEquals,
190 "Image gets from clipboard equals to image sets to the clipboard");
192 done();
193 });
194 }
196 exports["test Set Image Type Not Supported"] = function(assert) {
197 var clip = require("sdk/clipboard");
198 var flavor = "image";
200 assert.throws(function () {
201 clip.set(base64jpeg, flavor);
202 }, "Invalid flavor for image/jpeg");
204 };
206 // Notice that `imageTools.decodeImageData`, used by `clipboard.set` method for
207 // images, write directly to the javascript console the error in case the image
208 // is corrupt, even if the error is catched.
209 //
210 // See: http://mxr.mozilla.org/mozilla-central/source/image/src/Decoder.cpp#136
211 exports["test Set Image Type Wrong Data"] = function(assert) {
212 var clip = require("sdk/clipboard");
213 var flavor = "image";
215 var wrongPNG = "data:image/png" + base64jpeg.substr(15);
217 assert.throws(function () {
218 clip.set(wrongPNG, flavor);
219 }, "Unable to decode data given in a valid image.");
220 };
222 require("test").run(exports)