test_headers.js (5948B)
1 // 2 // cleaner HTTP header test infrastructure 3 // 4 // tests bugs: 589292, [add more here: see hg log for definitive list] 5 // 6 // TO ADD NEW TESTS: 7 // 1) Increment up 'lastTest' to new number (say, "99") 8 // 2) Add new test 'handler99' and 'completeTest99' functions. 9 // 3) If your test should fail the necko channel, set 10 // test_flags[99] = CL_EXPECT_FAILURE. 11 // 12 // TO DEBUG JUST ONE TEST: temporarily change firstTest and lastTest to equal 13 // the test # you're interested in. 14 // 15 // For tests that need duplicate copies of headers to be sent, see 16 // test_duplicate_headers.js 17 18 "use strict"; 19 20 var firstTest = 1; // set to test of interest when debugging 21 var lastTest = 4; // set to test of interest when debugging 22 //////////////////////////////////////////////////////////////////////////////// 23 24 // Note: sets Cc and Ci variables 25 26 const { HttpServer } = ChromeUtils.importESModule( 27 "resource://testing-common/httpd.sys.mjs" 28 ); 29 30 ChromeUtils.defineLazyGetter(this, "URL", function () { 31 return "http://localhost:" + httpserver.identity.primaryPort; 32 }); 33 34 var httpserver = new HttpServer(); 35 var nextTest = firstTest; 36 var test_flags = []; 37 var testPathBase = "/test_headers"; 38 39 function run_test() { 40 httpserver.start(-1); 41 42 do_test_pending(); 43 run_test_number(nextTest); 44 } 45 46 function runNextTest() { 47 if (nextTest == lastTest) { 48 endTests(); 49 return; 50 } 51 nextTest++; 52 // Make sure test functions exist 53 if (globalThis["handler" + nextTest] == undefined) { 54 do_throw("handler" + nextTest + " undefined!"); 55 } 56 if (globalThis["completeTest" + nextTest] == undefined) { 57 do_throw("completeTest" + nextTest + " undefined!"); 58 } 59 60 run_test_number(nextTest); 61 } 62 63 function run_test_number(num) { 64 let testPath = testPathBase + num; 65 httpserver.registerPathHandler(testPath, globalThis["handler" + num]); 66 67 var channel = setupChannel(testPath); 68 let flags = test_flags[num]; // OK if flags undefined for test 69 channel.asyncOpen( 70 new ChannelListener(globalThis["completeTest" + num], channel, flags) 71 ); 72 } 73 74 function setupChannel(url) { 75 var chan = NetUtil.newChannel({ 76 uri: URL + url, 77 loadUsingSystemPrincipal: true, 78 }); 79 var httpChan = chan.QueryInterface(Ci.nsIHttpChannel); 80 return httpChan; 81 } 82 83 function endTests() { 84 httpserver.stop(do_test_finished); 85 } 86 87 //////////////////////////////////////////////////////////////////////////////// 88 // Test 1: test Content-Disposition channel attributes 89 // eslint-disable-next-line no-unused-vars 90 function handler1(metadata, response) { 91 response.setStatusLine(metadata.httpVersion, 200, "OK"); 92 response.setHeader("Content-Disposition", "attachment; filename=foo"); 93 response.setHeader("Content-Type", "text/plain", false); 94 } 95 96 // eslint-disable-next-line no-unused-vars 97 function completeTest1(request) { 98 try { 99 var chan = request.QueryInterface(Ci.nsIChannel); 100 Assert.equal(chan.contentDisposition, chan.DISPOSITION_ATTACHMENT); 101 Assert.equal(chan.contentDispositionFilename, "foo"); 102 Assert.equal(chan.contentDispositionHeader, "attachment; filename=foo"); 103 } catch (ex) { 104 do_throw("error parsing Content-Disposition: " + ex); 105 } 106 runNextTest(); 107 } 108 109 //////////////////////////////////////////////////////////////////////////////// 110 // Test 2: no filename 111 // eslint-disable-next-line no-unused-vars 112 function handler2(metadata, response) { 113 response.setStatusLine(metadata.httpVersion, 200, "OK"); 114 response.setHeader("Content-Type", "text/plain", false); 115 response.setHeader("Content-Disposition", "attachment"); 116 var body = "foo"; 117 response.bodyOutputStream.write(body, body.length); 118 } 119 120 // eslint-disable-next-line no-unused-vars 121 function completeTest2(request) { 122 try { 123 var chan = request.QueryInterface(Ci.nsIChannel); 124 Assert.equal(chan.contentDisposition, chan.DISPOSITION_ATTACHMENT); 125 Assert.equal(chan.contentDispositionHeader, "attachment"); 126 chan.contentDispositionFilename; // should barf 127 do_throw("Should have failed getting Content-Disposition filename"); 128 } catch (ex) { 129 info("correctly ate exception"); 130 } 131 runNextTest(); 132 } 133 134 //////////////////////////////////////////////////////////////////////////////// 135 // Test 3: filename missing 136 // eslint-disable-next-line no-unused-vars 137 function handler3(metadata, response) { 138 response.setStatusLine(metadata.httpVersion, 200, "OK"); 139 response.setHeader("Content-Type", "text/plain", false); 140 response.setHeader("Content-Disposition", "attachment; filename="); 141 var body = "foo"; 142 response.bodyOutputStream.write(body, body.length); 143 } 144 145 // eslint-disable-next-line no-unused-vars 146 function completeTest3(request) { 147 try { 148 var chan = request.QueryInterface(Ci.nsIChannel); 149 Assert.equal(chan.contentDisposition, chan.DISPOSITION_ATTACHMENT); 150 Assert.equal(chan.contentDispositionHeader, "attachment; filename="); 151 chan.contentDispositionFilename; // should barf 152 153 do_throw("Should have failed getting Content-Disposition filename"); 154 } catch (ex) { 155 info("correctly ate exception"); 156 } 157 runNextTest(); 158 } 159 160 //////////////////////////////////////////////////////////////////////////////// 161 // Test 4: inline 162 // eslint-disable-next-line no-unused-vars 163 function handler4(metadata, response) { 164 response.setStatusLine(metadata.httpVersion, 200, "OK"); 165 response.setHeader("Content-Type", "text/plain", false); 166 response.setHeader("Content-Disposition", "inline"); 167 var body = "foo"; 168 response.bodyOutputStream.write(body, body.length); 169 } 170 171 // eslint-disable-next-line no-unused-vars 172 function completeTest4(request) { 173 try { 174 var chan = request.QueryInterface(Ci.nsIChannel); 175 Assert.equal(chan.contentDisposition, chan.DISPOSITION_INLINE); 176 Assert.equal(chan.contentDispositionHeader, "inline"); 177 178 chan.contentDispositionFilename; // should barf 179 do_throw("Should have failed getting Content-Disposition filename"); 180 } catch (ex) { 181 info("correctly ate exception"); 182 } 183 runNextTest(); 184 }