michael@0: /* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ michael@0: Components.utils.import("resource://gre/modules/NetUtil.jsm"); michael@0: michael@0: var gIoService = Components.classes["@mozilla.org/network/io-service;1"] michael@0: .getService(Components.interfaces.nsIIOService); michael@0: michael@0: michael@0: // Run by: cd objdir; make -C netwerk/test/ xpcshell-tests michael@0: // or: cd objdir; make SOLO_FILE="test_URIs.js" -C netwerk/test/ check-one michael@0: michael@0: // See also test_URIs2.js. michael@0: michael@0: // Relevant RFCs: 1738, 1808, 2396, 3986 (newer than the code) michael@0: // http://greenbytes.de/tech/webdav/rfc3986.html#rfc.section.5.4 michael@0: // http://greenbytes.de/tech/tc/uris/ michael@0: michael@0: // TEST DATA michael@0: // --------- michael@0: var gTests = [ michael@0: { spec: "about:blank", michael@0: scheme: "about", michael@0: prePath: "about:", michael@0: path: "blank", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: true, immutable: true }, michael@0: { spec: "about:foobar", michael@0: scheme: "about", michael@0: prePath: "about:", michael@0: path: "foobar", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: false, immutable: true }, michael@0: { spec: "chrome://foobar/somedir/somefile.xml", michael@0: scheme: "chrome", michael@0: prePath: "chrome://foobar", michael@0: path: "/somedir/somefile.xml", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false, immutable: true }, michael@0: { spec: "data:text/html;charset=utf-8,", michael@0: scheme: "data", michael@0: prePath: "data:", michael@0: path: "text/html;charset=utf-8,", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: false }, michael@0: { spec: "data:text/html;charset=utf-8,\r\n\t", michael@0: scheme: "data", michael@0: prePath: "data:", michael@0: path: "text/html;charset=utf-8,", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: false }, michael@0: { spec: "data:text/plain,hello world", michael@0: scheme: "data", michael@0: prePath: "data:", michael@0: path: "text/plain,hello%20world", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: false }, michael@0: { spec: "file:///dir/afile", michael@0: scheme: "data", michael@0: prePath: "data:", michael@0: path: "text/plain,2", michael@0: ref: "", michael@0: relativeURI: "data:te\nxt/plain,2", michael@0: nsIURL: false, nsINestedURI: false }, michael@0: { spec: "file://", michael@0: scheme: "file", michael@0: prePath: "file://", michael@0: path: "/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "file:///", michael@0: scheme: "file", michael@0: prePath: "file://", michael@0: path: "/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "file:///myFile.html", michael@0: scheme: "file", michael@0: prePath: "file://", michael@0: path: "/myFile.html", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "file:///dir/afile", michael@0: scheme: "file", michael@0: prePath: "file://", michael@0: path: "/dir/data/text/plain,2", michael@0: ref: "", michael@0: relativeURI: "data/text/plain,2", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "file:///dir/dir2/", michael@0: scheme: "file", michael@0: prePath: "file://", michael@0: path: "/dir/dir2/data/text/plain,2", michael@0: ref: "", michael@0: relativeURI: "data/text/plain,2", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "ftp://", michael@0: scheme: "ftp", michael@0: prePath: "ftp://", michael@0: path: "/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "ftp:///", michael@0: scheme: "ftp", michael@0: prePath: "ftp://", michael@0: path: "/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "ftp://ftp.mozilla.org/pub/mozilla.org/README", michael@0: scheme: "ftp", michael@0: prePath: "ftp://ftp.mozilla.org", michael@0: path: "/pub/mozilla.org/README", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "ftp://foo:bar@ftp.mozilla.org:100/pub/mozilla.org/README", michael@0: scheme: "ftp", michael@0: prePath: "ftp://foo:bar@ftp.mozilla.org:100", michael@0: port: 100, michael@0: username: "foo", michael@0: password: "bar", michael@0: path: "/pub/mozilla.org/README", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "ftp://foo:@ftp.mozilla.org:100/pub/mozilla.org/README", michael@0: scheme: "ftp", michael@0: prePath: "ftp://foo:@ftp.mozilla.org:100", michael@0: port: 100, michael@0: username: "foo", michael@0: password: "", michael@0: path: "/pub/mozilla.org/README", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: //Bug 706249 michael@0: { spec: "http:x:@", michael@0: scheme: "http", michael@0: prePath: "http://x:@", michael@0: username: "x", michael@0: password: "", michael@0: path: "", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "gopher://mozilla.org/", michael@0: scheme: "gopher", michael@0: prePath: "gopher:", michael@0: path: "//mozilla.org/", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: false }, michael@0: { spec: "http://", michael@0: scheme: "http", michael@0: prePath: "http://", michael@0: path: "/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "http:///", michael@0: scheme: "http", michael@0: prePath: "http://", michael@0: path: "/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "http://www.example.com/", michael@0: scheme: "http", michael@0: prePath: "http://www.example.com", michael@0: path: "/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "http://www.exa\nmple.com/", michael@0: scheme: "http", michael@0: prePath: "http://www.example.com", michael@0: path: "/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "http://10.32.4.239/", michael@0: scheme: "http", michael@0: prePath: "http://10.32.4.239", michael@0: host: "10.32.4.239", michael@0: path: "/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "http://[::192.9.5.5]/ipng", michael@0: scheme: "http", michael@0: prePath: "http://[::192.9.5.5]", michael@0: host: "::192.9.5.5", michael@0: path: "/ipng", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "http://[FEDC:BA98:7654:3210:FEDC:BA98:7654:3210]:8888/index.html", michael@0: scheme: "http", michael@0: prePath: "http://[fedc:ba98:7654:3210:fedc:ba98:7654:3210]:8888", michael@0: host: "fedc:ba98:7654:3210:fedc:ba98:7654:3210", michael@0: port: 8888, michael@0: path: "/index.html", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "http://bar:foo@www.mozilla.org:8080/pub/mozilla.org/README.html", michael@0: scheme: "http", michael@0: prePath: "http://bar:foo@www.mozilla.org:8080", michael@0: port: 8080, michael@0: username: "bar", michael@0: password: "foo", michael@0: host: "www.mozilla.org", michael@0: path: "/pub/mozilla.org/README.html", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "jar:resource://!/", michael@0: scheme: "jar", michael@0: prePath: "jar:", michael@0: path: "resource:///!/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: true }, michael@0: { spec: "jar:resource://gre/chrome.toolkit.jar!/", michael@0: scheme: "jar", michael@0: prePath: "jar:", michael@0: path: "resource://gre/chrome.toolkit.jar!/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: true }, michael@0: { spec: "mailto:webmaster@mozilla.com", michael@0: scheme: "mailto", michael@0: prePath: "mailto:", michael@0: path: "webmaster@mozilla.com", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: false }, michael@0: { spec: "javascript:new Date()", michael@0: scheme: "javascript", michael@0: prePath: "javascript:", michael@0: path: "new%20Date()", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: false }, michael@0: { spec: "blob:123456", michael@0: scheme: "blob", michael@0: prePath: "blob:", michael@0: path: "123456", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: false, immutable: true }, michael@0: { spec: "place:sort=8&maxResults=10", michael@0: scheme: "place", michael@0: prePath: "place:", michael@0: path: "sort=8&maxResults=10", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: false }, michael@0: { spec: "resource://gre/", michael@0: scheme: "resource", michael@0: prePath: "resource://gre", michael@0: path: "/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "resource://gre/components/", michael@0: scheme: "resource", michael@0: prePath: "resource://gre", michael@0: path: "/components/", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: { spec: "view-source:about:blank", michael@0: scheme: "view-source", michael@0: prePath: "view-source:", michael@0: path: "about:blank", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: true, immutable: true }, michael@0: { spec: "view-source:http://www.mozilla.org/", michael@0: scheme: "view-source", michael@0: prePath: "view-source:", michael@0: path: "http://www.mozilla.org/", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: true, immutable: true }, michael@0: { spec: "x-external:", michael@0: scheme: "x-external", michael@0: prePath: "x-external:", michael@0: path: "", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: false }, michael@0: { spec: "x-external:abc", michael@0: scheme: "x-external", michael@0: prePath: "x-external:", michael@0: path: "abc", michael@0: ref: "", michael@0: nsIURL: false, nsINestedURI: false }, michael@0: { spec: "http://www2.example.com/", michael@0: relativeURI: "a/b/c/d", michael@0: scheme: "http", michael@0: prePath: "http://www2.example.com", michael@0: path: "/a/b/c/d", michael@0: ref: "", michael@0: nsIURL: true, nsINestedURI: false }, michael@0: michael@0: // Adding more? Consider adding to test_URIs2.js instead, so that neither michael@0: // test runs for *too* long, risking timeouts on slow platforms. michael@0: ]; michael@0: michael@0: var gHashSuffixes = [ michael@0: "#", michael@0: "#myRef", michael@0: "#myRef?a=b", michael@0: "#myRef#", michael@0: "#myRef#x:yz" michael@0: ]; michael@0: michael@0: // TEST HELPER FUNCTIONS michael@0: // --------------------- michael@0: function do_info(text, stack) { michael@0: if (!stack) michael@0: stack = Components.stack.caller; michael@0: michael@0: dump( "\n" + michael@0: "TEST-INFO | " + stack.filename + " | [" + stack.name + " : " + michael@0: stack.lineNumber + "] " + text + "\n"); michael@0: } michael@0: michael@0: // Checks that the URIs satisfy equals(), in both possible orderings. michael@0: // Also checks URI.equalsExceptRef(), because equal URIs should also be equal michael@0: // when we ignore the ref. michael@0: // michael@0: // The third argument is optional. If the client passes a third argument michael@0: // (e.g. todo_check_true), we'll use that in lieu of do_check_true. michael@0: function do_check_uri_eq(aURI1, aURI2, aCheckTrueFunc) { michael@0: if (!aCheckTrueFunc) { michael@0: aCheckTrueFunc = do_check_true; michael@0: } michael@0: michael@0: do_info("(uri equals check: '" + aURI1.spec + "' == '" + aURI2.spec + "')"); michael@0: aCheckTrueFunc(aURI1.equals(aURI2)); michael@0: do_info("(uri equals check: '" + aURI2.spec + "' == '" + aURI1.spec + "')"); michael@0: aCheckTrueFunc(aURI2.equals(aURI1)); michael@0: michael@0: // (Only take the extra step of testing 'equalsExceptRef' when we expect the michael@0: // URIs to really be equal. In 'todo' cases, the URIs may or may not be michael@0: // equal when refs are ignored - there's no way of knowing in general.) michael@0: if (aCheckTrueFunc == do_check_true) { michael@0: do_check_uri_eqExceptRef(aURI1, aURI2, aCheckTrueFunc); michael@0: } michael@0: } michael@0: michael@0: // Checks that the URIs satisfy equalsExceptRef(), in both possible orderings. michael@0: // michael@0: // The third argument is optional. If the client passes a third argument michael@0: // (e.g. todo_check_true), we'll use that in lieu of do_check_true. michael@0: function do_check_uri_eqExceptRef(aURI1, aURI2, aCheckTrueFunc) { michael@0: if (!aCheckTrueFunc) { michael@0: aCheckTrueFunc = do_check_true; michael@0: } michael@0: michael@0: do_info("(uri equalsExceptRef check: '" + michael@0: aURI1.spec + "' == '" + aURI2.spec + "')"); michael@0: aCheckTrueFunc(aURI1.equalsExceptRef(aURI2)); michael@0: do_info("(uri equalsExceptRef check: '" + michael@0: aURI2.spec + "' == '" + aURI1.spec + "')"); michael@0: aCheckTrueFunc(aURI2.equalsExceptRef(aURI1)); michael@0: } michael@0: michael@0: // Checks that the given property on aURI matches the corresponding property michael@0: // in the test bundle (or matches some function of that corresponding property, michael@0: // if aTestFunctor is passed in). michael@0: function do_check_property(aTest, aURI, aPropertyName, aTestFunctor) { michael@0: if (aTest[aPropertyName]) { michael@0: var expectedVal = aTestFunctor ? michael@0: aTestFunctor(aTest[aPropertyName]) : michael@0: aTest[aPropertyName]; michael@0: michael@0: do_info("testing " + aPropertyName + " of " + michael@0: (aTestFunctor ? "modified '" : "'" ) + aTest.spec + michael@0: "' is '" + expectedVal + "'"); michael@0: do_check_eq(aURI[aPropertyName], expectedVal); michael@0: } michael@0: } michael@0: michael@0: // Test that a given URI parses correctly into its various components. michael@0: function do_test_uri_basic(aTest) { michael@0: var URI; michael@0: michael@0: do_info("Basic tests for " + aTest.spec + " relative URI: " + aTest.relativeURI); michael@0: michael@0: try { michael@0: URI = NetUtil.newURI(aTest.spec); michael@0: } catch(e) { michael@0: do_info("Caught error on parse of" + aTest.spec + " Error: " + e.result); michael@0: if (aTest.fail) { michael@0: do_check_eq(e.result, aTest.result); michael@0: return; michael@0: } michael@0: do_throw(e.result); michael@0: } michael@0: michael@0: if (aTest.relativeURI) { michael@0: var relURI; michael@0: michael@0: try { michael@0: relURI = gIoService.newURI(aTest.relativeURI, null, URI); michael@0: } catch (e) { michael@0: do_info("Caught error on Relative parse of " + aTest.spec + " + " + aTest.relativeURI +" Error: " + e.result); michael@0: if (aTest.relativeFail) { michael@0: do_check_eq(e.result, aTest.relativeFail); michael@0: return; michael@0: } michael@0: do_throw(e.result); michael@0: } michael@0: do_info("relURI.path = " + relURI.path + ", was " + URI.path); michael@0: URI = relURI; michael@0: do_info("URI.path now = " + URI.path); michael@0: } michael@0: michael@0: // Sanity-check michael@0: do_info("testing " + aTest.spec + " equals a clone of itself"); michael@0: do_check_uri_eq(URI, URI.clone()); michael@0: do_check_uri_eqExceptRef(URI, URI.cloneIgnoringRef()); michael@0: do_info("testing " + aTest.spec + " instanceof nsIURL"); michael@0: do_check_eq(URI instanceof Ci.nsIURL, aTest.nsIURL); michael@0: do_info("testing " + aTest.spec + " instanceof nsINestedURI"); michael@0: do_check_eq(URI instanceof Ci.nsINestedURI, michael@0: aTest.nsINestedURI); michael@0: michael@0: do_info("testing that " + aTest.spec + " throws or returns false " + michael@0: "from equals(null)"); michael@0: // XXXdholbert At some point it'd probably be worth making this behavior michael@0: // (throwing vs. returning false) consistent across URI implementations. michael@0: var threw = false; michael@0: var isEqualToNull; michael@0: try { michael@0: isEqualToNull = URI.equals(null); michael@0: } catch(e) { michael@0: threw = true; michael@0: } michael@0: do_check_true(threw || !isEqualToNull); michael@0: michael@0: michael@0: // Check the various components michael@0: do_check_property(aTest, URI, "scheme"); michael@0: do_check_property(aTest, URI, "prePath"); michael@0: do_check_property(aTest, URI, "path"); michael@0: do_check_property(aTest, URI, "ref"); michael@0: do_check_property(aTest, URI, "port"); michael@0: do_check_property(aTest, URI, "username"); michael@0: do_check_property(aTest, URI, "password"); michael@0: do_check_property(aTest, URI, "host"); michael@0: do_check_property(aTest, URI, "specIgnoringRef"); michael@0: if ("hasRef" in aTest) { michael@0: do_info("testing hasref: " + aTest.hasRef + " vs " + URI.hasRef); michael@0: do_check_eq(aTest.hasRef, URI.hasRef); michael@0: } michael@0: } michael@0: michael@0: // Test that a given URI parses correctly when we add a given ref to the end michael@0: function do_test_uri_with_hash_suffix(aTest, aSuffix) { michael@0: do_info("making sure caller is using suffix that starts with '#'"); michael@0: do_check_eq(aSuffix[0], "#"); michael@0: michael@0: var origURI = NetUtil.newURI(aTest.spec); michael@0: var testURI; michael@0: michael@0: if (aTest.relativeURI) { michael@0: try { michael@0: origURI = gIoService.newURI(aTest.relativeURI, null, origURI); michael@0: } catch (e) { michael@0: do_info("Caught error on Relative parse of " + aTest.spec + " + " + aTest.relativeURI +" Error: " + e.result); michael@0: return; michael@0: } michael@0: try { michael@0: testURI = gIoService.newURI(aSuffix, null, origURI); michael@0: } catch (e) { michael@0: do_info("Caught error adding suffix to " + aTest.spec + " + " + aTest.relativeURI + ", suffix " + aSuffix + " Error: " + e.result); michael@0: return; michael@0: } michael@0: } else { michael@0: testURI = NetUtil.newURI(aTest.spec + aSuffix); michael@0: } michael@0: michael@0: do_info("testing " + aTest.spec + " with '" + aSuffix + "' appended " + michael@0: "equals a clone of itself"); michael@0: do_check_uri_eq(testURI, testURI.clone()); michael@0: michael@0: do_info("testing " + aTest.spec + michael@0: " doesn't equal self with '" + aSuffix + "' appended"); michael@0: michael@0: do_check_false(origURI.equals(testURI)); michael@0: michael@0: do_info("testing " + aTest.spec + michael@0: " is equalExceptRef to self with '" + aSuffix + "' appended"); michael@0: do_check_uri_eqExceptRef(origURI, testURI); michael@0: michael@0: do_check_eq(testURI.hasRef, true); michael@0: michael@0: if (!origURI.ref) { michael@0: // These tests fail if origURI has a ref michael@0: do_info("testing cloneIgnoringRef on " + testURI.spec + michael@0: " is equal to no-ref version but not equal to ref version"); michael@0: var cloneNoRef = testURI.cloneIgnoringRef(); michael@0: do_check_uri_eq(cloneNoRef, origURI); michael@0: do_check_false(cloneNoRef.equals(testURI)); michael@0: } michael@0: michael@0: do_check_property(aTest, testURI, "scheme"); michael@0: do_check_property(aTest, testURI, "prePath"); michael@0: if (!origURI.ref) { michael@0: // These don't work if it's a ref already because '+' doesn't give the right result michael@0: do_check_property(aTest, testURI, "path", michael@0: function(aStr) { return aStr + aSuffix; }); michael@0: do_check_property(aTest, testURI, "ref", michael@0: function(aStr) { return aSuffix.substr(1); }); michael@0: } michael@0: } michael@0: michael@0: // Tests various ways of setting & clearing a ref on a URI. michael@0: function do_test_mutate_ref(aTest, aSuffix) { michael@0: do_info("making sure caller is using suffix that starts with '#'"); michael@0: do_check_eq(aSuffix[0], "#"); michael@0: michael@0: var refURIWithSuffix = NetUtil.newURI(aTest.spec + aSuffix); michael@0: var refURIWithoutSuffix = NetUtil.newURI(aTest.spec); michael@0: michael@0: var testURI = NetUtil.newURI(aTest.spec); michael@0: michael@0: // First: Try setting .ref to our suffix michael@0: do_info("testing that setting .ref on " + aTest.spec + michael@0: " to '" + aSuffix + "' does what we expect"); michael@0: testURI.ref = aSuffix; michael@0: do_check_uri_eq(testURI, refURIWithSuffix); michael@0: do_check_uri_eqExceptRef(testURI, refURIWithoutSuffix); michael@0: michael@0: // Now try setting .ref but leave off the initial hash (expect same result) michael@0: var suffixLackingHash = aSuffix.substr(1); michael@0: if (suffixLackingHash) { // (skip this our suffix was *just* a #) michael@0: do_info("testing that setting .ref on " + aTest.spec + michael@0: " to '" + suffixLackingHash + "' does what we expect"); michael@0: testURI.ref = suffixLackingHash; michael@0: do_check_uri_eq(testURI, refURIWithSuffix); michael@0: do_check_uri_eqExceptRef(testURI, refURIWithoutSuffix); michael@0: } michael@0: michael@0: // Now, clear .ref (should get us back the original spec) michael@0: do_info("testing that clearing .ref on " + testURI.spec + michael@0: " does what we expect"); michael@0: testURI.ref = ""; michael@0: do_check_uri_eq(testURI, refURIWithoutSuffix); michael@0: do_check_uri_eqExceptRef(testURI, refURIWithSuffix); michael@0: michael@0: if (!aTest.relativeURI) { michael@0: // TODO: These tests don't work as-is for relative URIs. michael@0: michael@0: // Now try setting .spec directly (including suffix) and then clearing .ref michael@0: var specWithSuffix = aTest.spec + aSuffix; michael@0: do_info("testing that setting spec to " + michael@0: specWithSuffix + " and then clearing ref does what we expect"); michael@0: testURI.spec = specWithSuffix; michael@0: testURI.ref = ""; michael@0: do_check_uri_eq(testURI, refURIWithoutSuffix); michael@0: do_check_uri_eqExceptRef(testURI, refURIWithSuffix); michael@0: michael@0: // XXX nsIJARURI throws an exception in SetPath(), so skip it for next part. michael@0: if (!(testURI instanceof Ci.nsIJARURI)) { michael@0: // Now try setting .path directly (including suffix) and then clearing .ref michael@0: // (same as above, but with now with .path instead of .spec) michael@0: testURI = NetUtil.newURI(aTest.spec); michael@0: michael@0: var pathWithSuffix = aTest.path + aSuffix; michael@0: do_info("testing that setting path to " + michael@0: pathWithSuffix + " and then clearing ref does what we expect"); michael@0: testURI.path = pathWithSuffix; michael@0: testURI.ref = ""; michael@0: do_check_uri_eq(testURI, refURIWithoutSuffix); michael@0: do_check_uri_eqExceptRef(testURI, refURIWithSuffix); michael@0: michael@0: // Also: make sure that clearing .path also clears .ref michael@0: testURI.path = pathWithSuffix; michael@0: do_info("testing that clearing path from " + michael@0: pathWithSuffix + " also clears .ref"); michael@0: testURI.path = ""; michael@0: do_check_eq(testURI.ref, ""); michael@0: } michael@0: } michael@0: } michael@0: michael@0: // Tests that normally-mutable properties can't be modified on michael@0: // special URIs that are known to be immutable. michael@0: function do_test_immutable(aTest) { michael@0: do_check_true(aTest.immutable); michael@0: michael@0: var URI = NetUtil.newURI(aTest.spec); michael@0: // All the non-readonly attributes on nsIURI.idl: michael@0: var propertiesToCheck = ["spec", "scheme", "userPass", "username", "password", michael@0: "hostPort", "host", "port", "path", "ref"]; michael@0: michael@0: propertiesToCheck.forEach(function(aProperty) { michael@0: var threw = false; michael@0: try { michael@0: URI[aProperty] = "anothervalue"; michael@0: } catch(e) { michael@0: threw = true; michael@0: } michael@0: michael@0: do_info("testing that setting '" + aProperty + michael@0: "' on immutable URI '" + aTest.spec + "' will throw"); michael@0: do_check_true(threw); michael@0: }); michael@0: } michael@0: michael@0: michael@0: // TEST MAIN FUNCTION michael@0: // ------------------ michael@0: function run_test() michael@0: { michael@0: // UTF-8 check - From bug 622981 michael@0: // ASCII michael@0: let base = gIoService.newURI("http://example.org/xenia?", null, null); michael@0: let resolved = gIoService.newURI("?x", null, base); michael@0: let expected = gIoService.newURI("http://example.org/xenia?x", michael@0: null, null); michael@0: do_info("Bug 662981: ACSII - comparing " + resolved.spec + " and " + expected.spec); michael@0: do_check_true(resolved.equals(expected)); michael@0: michael@0: // UTF-8 character "è" michael@0: // Bug 622981 was triggered by an empty query string michael@0: base = gIoService.newURI("http://example.org/xènia?", null, null); michael@0: resolved = gIoService.newURI("?x", null, base); michael@0: expected = gIoService.newURI("http://example.org/xènia?x", michael@0: null, null); michael@0: do_info("Bug 662981: UTF8 - comparing " + resolved.spec + " and " + expected.spec); michael@0: do_check_true(resolved.equals(expected)); michael@0: michael@0: gTests.forEach(function(aTest) { michael@0: // Check basic URI functionality michael@0: do_test_uri_basic(aTest); michael@0: michael@0: if (!aTest.fail) { michael@0: // Try adding various #-prefixed strings to the ends of the URIs michael@0: gHashSuffixes.forEach(function(aSuffix) { michael@0: do_test_uri_with_hash_suffix(aTest, aSuffix); michael@0: if (!aTest.immutable) { michael@0: do_test_mutate_ref(aTest, aSuffix); michael@0: } michael@0: }); michael@0: michael@0: // For URIs that we couldn't mutate above due to them being immutable: michael@0: // Now we check that they're actually immutable. michael@0: if (aTest.immutable) { michael@0: do_test_immutable(aTest); michael@0: } michael@0: } michael@0: }); michael@0: }