modules/libjar/test/unit/test_jarchannel.js

changeset 0
6474c204b198
equal deleted inserted replaced
-1:000000000000 0:5549b4364434
1 /* Any copyright is dedicated to the Public Domain.
2 * http://creativecommons.org/publicdomain/zero/1.0/
3 */
4
5 /**
6 * Tests some basic jar channel functionality
7 */
8
9
10 const {classes: Cc,
11 interfaces: Ci,
12 results: Cr,
13 Constructor: ctor
14 } = Components;
15
16 const ios = Cc["@mozilla.org/network/io-service;1"].
17 getService(Ci.nsIIOService);
18 const dirSvc = Cc["@mozilla.org/file/directory_service;1"].
19 getService(Ci.nsIProperties);
20 const obs = Cc["@mozilla.org/observer-service;1"].
21 getService(Ci.nsIObserverService);
22
23 const nsIBinaryInputStream = ctor("@mozilla.org/binaryinputstream;1",
24 "nsIBinaryInputStream",
25 "setInputStream"
26 );
27
28 const fileBase = "test_bug637286.zip";
29 const file = do_get_file("data/" + fileBase);
30 // on child we'll test with jar:remoteopenfile:// instead of jar:file://
31 const jarBase = "jar:" + filePrefix + ios.newFileURI(file).spec + "!";
32 const tmpDir = dirSvc.get("TmpD", Ci.nsIFile);
33
34 function Listener(callback) {
35 this._callback = callback;
36 }
37 Listener.prototype = {
38 gotStartRequest: false,
39 available: -1,
40 gotStopRequest: false,
41 QueryInterface: function(iid) {
42 if (iid.equals(Ci.nsISupports) ||
43 iid.equals(Ci.nsIRequestObserver))
44 return this;
45 throw Cr.NS_ERROR_NO_INTERFACE;
46 },
47 onDataAvailable: function(request, ctx, stream, offset, count) {
48 try {
49 this.available = stream.available();
50 do_check_eq(this.available, count);
51 // Need to consume stream to avoid assertion
52 new nsIBinaryInputStream(stream).readBytes(count);
53 }
54 catch (ex) {
55 do_throw(ex);
56 }
57 },
58 onStartRequest: function(request, ctx) {
59 this.gotStartRequest = true;
60 },
61 onStopRequest: function(request, ctx) {
62 this.gotStopRequest = true;
63 if (this._callback) {
64 this._callback.call(null, this);
65 }
66 }
67 };
68
69 /**
70 * Basic reading test for asynchronously opened jar channel
71 */
72 function testAsync() {
73 var uri = jarBase + "/inner40.zip";
74 var chan = ios.newChannel(uri, null, null);
75 do_check_true(chan.contentLength < 0);
76 chan.asyncOpen(new Listener(function(l) {
77 do_check_true(chan.contentLength > 0);
78 do_check_true(l.gotStartRequest);
79 do_check_true(l.gotStopRequest);
80 do_check_eq(l.available, chan.contentLength);
81
82 run_next_test();
83 }), null);
84 }
85
86 add_test(testAsync);
87 // Run same test again so we test the codepath for a zipcache hit
88 add_test(testAsync);
89
90
91 // In e10s child processes we don't currently support
92 // 1) synchronously opening jar files on parent
93 // 2) nested jar channels in e10s: (app:// doesn't use them).
94 // 3) we can't do file lock checks on android, so skip those tests too.
95 if (!inChild) {
96
97 /**
98 * Basic reading test for synchronously opened jar channels
99 */
100 add_test(function testSync() {
101 var uri = jarBase + "/inner40.zip";
102 var chan = ios.newChannel(uri, null, null);
103 var stream = chan.open();
104 do_check_true(chan.contentLength > 0);
105 do_check_eq(stream.available(), chan.contentLength);
106 stream.close();
107 stream.close(); // should still not throw
108
109 run_next_test();
110 });
111
112
113 /**
114 * Basic reading test for synchronously opened, nested jar channels
115 */
116 add_test(function testSyncNested() {
117 var uri = "jar:" + jarBase + "/inner40.zip!/foo";
118 var chan = ios.newChannel(uri, null, null);
119 var stream = chan.open();
120 do_check_true(chan.contentLength > 0);
121 do_check_eq(stream.available(), chan.contentLength);
122 stream.close();
123 stream.close(); // should still not throw
124
125 run_next_test();
126 });
127
128 /**
129 * Basic reading test for asynchronously opened, nested jar channels
130 */
131 add_test(function testAsyncNested(next) {
132 var uri = "jar:" + jarBase + "/inner40.zip!/foo";
133 var chan = ios.newChannel(uri, null, null);
134 chan.asyncOpen(new Listener(function(l) {
135 do_check_true(chan.contentLength > 0);
136 do_check_true(l.gotStartRequest);
137 do_check_true(l.gotStopRequest);
138 do_check_eq(l.available, chan.contentLength);
139
140 run_next_test();
141 }), null);
142 });
143
144 /**
145 * Verify that file locks are released when closing a synchronously
146 * opened jar channel stream
147 */
148 add_test(function testSyncCloseUnlocks() {
149 var copy = tmpDir.clone();
150 copy.append(fileBase);
151 file.copyTo(copy.parent, copy.leafName);
152
153 var uri = "jar:" + ios.newFileURI(copy).spec + "!/inner40.zip";
154 var chan = ios.newChannel(uri, null, null);
155 var stream = chan.open();
156 do_check_true(chan.contentLength > 0);
157 stream.close();
158
159 // Drop any jar caches
160 obs.notifyObservers(null, "chrome-flush-caches", null);
161
162 try {
163 copy.remove(false);
164 }
165 catch (ex) {
166 do_throw(ex);
167 }
168
169 run_next_test();
170 });
171
172 /**
173 * Verify that file locks are released when closing an asynchronously
174 * opened jar channel stream
175 */
176 add_test(function testAsyncCloseUnlocks() {
177 var copy = tmpDir.clone();
178 copy.append(fileBase);
179 file.copyTo(copy.parent, copy.leafName);
180
181 var uri = "jar:" + ios.newFileURI(copy).spec + "!/inner40.zip";
182 var chan = ios.newChannel(uri, null, null);
183 chan.asyncOpen(new Listener(function (l) {
184 do_check_true(chan.contentLength > 0);
185
186 // Drop any jar caches
187 obs.notifyObservers(null, "chrome-flush-caches", null);
188
189 try {
190 copy.remove(false);
191 }
192 catch (ex) {
193 do_throw(ex);
194 }
195
196 run_next_test();
197 }), null);
198 });
199
200 } // if !inChild
201
202 function run_test() run_next_test();

mercurial