1/* 2 * Copyright (C) 2007 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package android.net; 18 19import android.content.ContentUris; 20import android.os.Parcel; 21import android.test.suitebuilder.annotation.SmallTest; 22 23import junit.framework.TestCase; 24 25import java.io.File; 26import java.util.Arrays; 27import java.util.Iterator; 28import java.util.List; 29import java.util.Set; 30 31public class UriTest extends TestCase { 32 33 @SmallTest 34 public void testToStringWithPathOnly() { 35 Uri.Builder builder = new Uri.Builder(); 36 37 // Not a valid path, but this came from a user's test case. 38 builder.path("//foo"); 39 Uri uri = builder.build(); 40 assertEquals("//foo", uri.toString()); 41 } 42 43 @SmallTest 44 public void testParcelling() { 45 parcelAndUnparcel(Uri.parse("foo:bob%20lee")); 46 parcelAndUnparcel(Uri.fromParts("foo", "bob lee", "fragment")); 47 parcelAndUnparcel(new Uri.Builder() 48 .scheme("http") 49 .authority("crazybob.org") 50 .path("/rss/") 51 .encodedQuery("a=b") 52 .fragment("foo") 53 .build()); 54 } 55 56 private void parcelAndUnparcel(Uri u) { 57 Parcel p = Parcel.obtain(); 58 try { 59 Uri.writeToParcel(p, u); 60 p.setDataPosition(0); 61 assertEquals(u, Uri.CREATOR.createFromParcel(p)); 62 63 p.setDataPosition(0); 64 u = u.buildUpon().build(); 65 Uri.writeToParcel(p, u); 66 p.setDataPosition(0); 67 assertEquals(u, Uri.CREATOR.createFromParcel(p)); 68 } 69 finally { 70 p.recycle(); 71 } 72 } 73 74 @SmallTest 75 public void testBuildUponOpaqueStringUri() { 76 Uri u = Uri.parse("bob:lee").buildUpon().scheme("robert").build(); 77 assertEquals("robert", u.getScheme()); 78 assertEquals("lee", u.getEncodedSchemeSpecificPart()); 79 assertEquals("lee", u.getSchemeSpecificPart()); 80 assertNull(u.getQuery()); 81 assertNull(u.getPath()); 82 assertNull(u.getAuthority()); 83 assertNull(u.getHost()); 84 } 85 86 @SmallTest 87 public void testStringUri() { 88 assertEquals("bob lee", 89 Uri.parse("foo:bob%20lee").getSchemeSpecificPart()); 90 assertEquals("bob%20lee", 91 Uri.parse("foo:bob%20lee").getEncodedSchemeSpecificPart()); 92 assertEquals("/bob%20lee", 93 Uri.parse("foo:/bob%20lee").getEncodedPath()); 94 assertNull(Uri.parse("foo:bob%20lee").getPath()); 95 assertEquals("bob%20lee", 96 Uri.parse("foo:?bob%20lee").getEncodedQuery()); 97 assertNull(Uri.parse("foo:bar#?bob%20lee").getQuery()); 98 assertEquals("bob%20lee", 99 Uri.parse("foo:#bob%20lee").getEncodedFragment()); 100 } 101 102 @SmallTest 103 public void testStringUriIsHierarchical() { 104 assertTrue(Uri.parse("bob").isHierarchical()); 105 assertFalse(Uri.parse("bob:").isHierarchical()); 106 } 107 108 @SmallTest 109 public void testNullUriString() { 110 try { 111 Uri.parse(null); 112 fail(); 113 } catch (NullPointerException e) {} 114 } 115 116 @SmallTest 117 public void testNullFile() { 118 try { 119 Uri.fromFile(null); 120 fail(); 121 } catch (NullPointerException e) {} 122 } 123 124 @SmallTest 125 public void testCompareTo() { 126 Uri a = Uri.parse("foo:a"); 127 Uri b = Uri.parse("foo:b"); 128 Uri b2 = Uri.parse("foo:b"); 129 130 assertTrue(a.compareTo(b) < 0); 131 assertTrue(b.compareTo(a) > 0); 132 assertEquals(0, b.compareTo(b2)); 133 } 134 135 @SmallTest 136 public void testEqualsAndHashCode() { 137 138 Uri a = Uri.parse("http://crazybob.org/test/?foo=bar#tee"); 139 140 Uri b = new Uri.Builder() 141 .scheme("http") 142 .authority("crazybob.org") 143 .path("/test/") 144 .encodedQuery("foo=bar") 145 .fragment("tee") 146 .build(); 147 148 // Try alternate builder methods. 149 Uri c = new Uri.Builder() 150 .scheme("http") 151 .encodedAuthority("crazybob.org") 152 .encodedPath("/test/") 153 .encodedQuery("foo=bar") 154 .encodedFragment("tee") 155 .build(); 156 157 assertFalse(Uri.EMPTY.equals(null)); 158 159 assertEquals(a, b); 160 assertEquals(b, c); 161 assertEquals(c, a); 162 163 assertEquals(a.hashCode(), b.hashCode()); 164 assertEquals(b.hashCode(), c.hashCode()); 165 } 166 167 @SmallTest 168 public void testAuthorityParsing() { 169 Uri uri = Uri.parse("http://localhost:42"); 170 assertEquals("localhost", uri.getHost()); 171 assertEquals(42, uri.getPort()); 172 173 uri = Uri.parse("http://bob@localhost:42"); 174 assertEquals("bob", uri.getUserInfo()); 175 assertEquals("localhost", uri.getHost()); 176 assertEquals(42, uri.getPort()); 177 178 uri = Uri.parse("http://bob%20lee@localhost:42"); 179 assertEquals("bob lee", uri.getUserInfo()); 180 assertEquals("bob%20lee", uri.getEncodedUserInfo()); 181 182 uri = Uri.parse("http://bob%40lee%3ajr@local%68ost:4%32"); 183 assertEquals("bob@lee:jr", uri.getUserInfo()); 184 assertEquals("localhost", uri.getHost()); 185 assertEquals(42, uri.getPort()); 186 187 uri = Uri.parse("http://localhost"); 188 assertEquals("localhost", uri.getHost()); 189 assertEquals(-1, uri.getPort()); 190 191 uri = Uri.parse("http://a:a@example.com:a@example2.com/path"); 192 assertEquals("a:a@example.com:a@example2.com", uri.getAuthority()); 193 assertEquals("example2.com", uri.getHost()); 194 assertEquals(-1, uri.getPort()); 195 assertEquals("/path", uri.getPath()); 196 197 uri = Uri.parse("http://a.foo.com\\.example.com/path"); 198 assertEquals("a.foo.com", uri.getHost()); 199 assertEquals(-1, uri.getPort()); 200 assertEquals("\\.example.com/path", uri.getPath()); 201 } 202 203 @SmallTest 204 public void testBuildUponOpaqueUri() { 205 Uri a = Uri.fromParts("foo", "bar", "tee"); 206 Uri b = a.buildUpon().fragment("new").build(); 207 assertEquals("new", b.getFragment()); 208 assertEquals("bar", b.getSchemeSpecificPart()); 209 assertEquals("foo", b.getScheme()); 210 } 211 212 @SmallTest 213 public void testBuildUponEncodedOpaqueUri() { 214 Uri a = new Uri.Builder() 215 .scheme("foo") 216 .encodedOpaquePart("bar") 217 .fragment("tee") 218 .build(); 219 Uri b = a.buildUpon().fragment("new").build(); 220 assertEquals("new", b.getFragment()); 221 assertEquals("bar", b.getSchemeSpecificPart()); 222 assertEquals("foo", b.getScheme()); 223 } 224 225 @SmallTest 226 public void testPathSegmentDecoding() { 227 Uri uri = Uri.parse("foo://bar/a%20a/b%20b"); 228 assertEquals("a a", uri.getPathSegments().get(0)); 229 assertEquals("b b", uri.getPathSegments().get(1)); 230 } 231 232 @SmallTest 233 public void testSms() { 234 Uri base = Uri.parse("content://sms"); 235 Uri appended = base.buildUpon() 236 .appendEncodedPath("conversations/addr=555-1212") 237 .build(); 238 assertEquals("content://sms/conversations/addr=555-1212", 239 appended.toString()); 240 assertEquals(2, appended.getPathSegments().size()); 241 assertEquals("conversations", appended.getPathSegments().get(0)); 242 assertEquals("addr=555-1212", appended.getPathSegments().get(1)); 243 } 244 245 @SmallTest 246 public void testEncodeWithAllowedChars() { 247 String encoded = Uri.encode("Bob:/", "/"); 248 assertEquals(-1, encoded.indexOf(':')); 249 assertTrue(encoded.indexOf('/') > -1); 250 } 251 252 @SmallTest 253 public void testEncodeDecode() { 254 code(null); 255 code(""); 256 code("Bob"); 257 code(":Bob"); 258 code("::Bob"); 259 code("Bob::Lee"); 260 code("Bob:Lee"); 261 code("Bob::"); 262 code("Bob:"); 263 code("::Bob::"); 264 } 265 266 private void code(String s) { 267 assertEquals(s, Uri.decode(Uri.encode(s, null))); 268 } 269 270 @SmallTest 271 public void testFile() { 272 File f = new File("/tmp/bob"); 273 274 Uri uri = Uri.fromFile(f); 275 276 assertEquals("file:///tmp/bob", uri.toString()); 277 } 278 279 @SmallTest 280 public void testQueryParameters() { 281 Uri uri = Uri.parse("content://user"); 282 283 assertEquals(null, uri.getQueryParameter("a")); 284 285 uri = uri.buildUpon().appendQueryParameter("a", "b").build(); 286 287 assertEquals("b", uri.getQueryParameter("a")); 288 289 uri = uri.buildUpon().appendQueryParameter("a", "b2").build(); 290 291 assertEquals(Arrays.asList("b", "b2"), uri.getQueryParameters("a")); 292 293 uri = uri.buildUpon().appendQueryParameter("c", "d").build(); 294 295 assertEquals(Arrays.asList("b", "b2"), uri.getQueryParameters("a")); 296 assertEquals("d", uri.getQueryParameter("c")); 297 } 298 299 // http://b/2337042 300 @SmallTest 301 public void testHostWithTrailingDot() { 302 Uri uri = Uri.parse("http://google.com./b/c/g"); 303 assertEquals("google.com.", uri.getHost()); 304 assertEquals("/b/c/g", uri.getPath()); 305 } 306 307 @SmallTest 308 public void testSchemeOnly() { 309 Uri uri = Uri.parse("empty:"); 310 assertEquals("empty", uri.getScheme()); 311 assertTrue(uri.isAbsolute()); 312 assertNull(uri.getPath()); 313 } 314 315 @SmallTest 316 public void testEmptyPath() { 317 Uri uri = Uri.parse("content://user"); 318 assertEquals(0, uri.getPathSegments().size()); 319 } 320 321 @SmallTest 322 public void testPathOperations() { 323 Uri uri = Uri.parse("content://user/a/b"); 324 325 assertEquals(2, uri.getPathSegments().size()); 326 assertEquals("b", uri.getLastPathSegment()); 327 328 Uri first = uri; 329 uri = uri.buildUpon().appendPath("c").build(); 330 331 assertEquals(3, uri.getPathSegments().size()); 332 assertEquals("c", uri.getLastPathSegment()); 333 assertEquals("content://user/a/b/c", uri.toString()); 334 335 uri = ContentUris.withAppendedId(uri, 100); 336 337 assertEquals(4, uri.getPathSegments().size()); 338 assertEquals("100", uri.getLastPathSegment()); 339 assertEquals(100, ContentUris.parseId(uri)); 340 assertEquals("content://user/a/b/c/100", uri.toString()); 341 342 // Make sure the original URI is still intact. 343 assertEquals(2, first.getPathSegments().size()); 344 assertEquals("b", first.getLastPathSegment()); 345 346 try { 347 first.getPathSegments().get(2); 348 fail(); 349 } catch (IndexOutOfBoundsException e) {} 350 351 assertEquals(null, Uri.EMPTY.getLastPathSegment()); 352 353 Uri withC = Uri.parse("foo:/a/b/").buildUpon().appendPath("c").build(); 354 assertEquals("/a/b/c", withC.getPath()); 355 } 356 357 @SmallTest 358 public void testOpaqueUri() { 359 Uri uri = Uri.parse("mailto:nobody"); 360 testOpaqueUri(uri); 361 362 uri = uri.buildUpon().build(); 363 testOpaqueUri(uri); 364 365 uri = Uri.fromParts("mailto", "nobody", null); 366 testOpaqueUri(uri); 367 368 uri = uri.buildUpon().build(); 369 testOpaqueUri(uri); 370 371 uri = new Uri.Builder() 372 .scheme("mailto") 373 .opaquePart("nobody") 374 .build(); 375 testOpaqueUri(uri); 376 377 uri = uri.buildUpon().build(); 378 testOpaqueUri(uri); 379 } 380 381 private void testOpaqueUri(Uri uri) { 382 assertEquals("mailto", uri.getScheme()); 383 assertEquals("nobody", uri.getSchemeSpecificPart()); 384 assertEquals("nobody", uri.getEncodedSchemeSpecificPart()); 385 386 assertNull(uri.getFragment()); 387 assertTrue(uri.isAbsolute()); 388 assertTrue(uri.isOpaque()); 389 assertFalse(uri.isRelative()); 390 assertFalse(uri.isHierarchical()); 391 392 assertNull(uri.getAuthority()); 393 assertNull(uri.getEncodedAuthority()); 394 assertNull(uri.getPath()); 395 assertNull(uri.getEncodedPath()); 396 assertNull(uri.getUserInfo()); 397 assertNull(uri.getEncodedUserInfo()); 398 assertNull(uri.getQuery()); 399 assertNull(uri.getEncodedQuery()); 400 assertNull(uri.getHost()); 401 assertEquals(-1, uri.getPort()); 402 403 assertTrue(uri.getPathSegments().isEmpty()); 404 assertNull(uri.getLastPathSegment()); 405 406 assertEquals("mailto:nobody", uri.toString()); 407 408 Uri withFragment = uri.buildUpon().fragment("top").build(); 409 assertEquals("mailto:nobody#top", withFragment.toString()); 410 } 411 412 @SmallTest 413 public void testHierarchicalUris() { 414 testHierarchical("http", "google.com", "/p1/p2", "query", "fragment"); 415 testHierarchical("file", null, "/p1/p2", null, null); 416 testHierarchical("content", "contact", "/p1/p2", null, null); 417 testHierarchical("http", "google.com", "/p1/p2", null, "fragment"); 418 testHierarchical("http", "google.com", "", null, "fragment"); 419 testHierarchical("http", "google.com", "", "query", "fragment"); 420 testHierarchical("http", "google.com", "", "query", null); 421 testHierarchical("http", null, "/", "query", null); 422 } 423 424 private static void testHierarchical(String scheme, String authority, 425 String path, String query, String fragment) { 426 StringBuilder sb = new StringBuilder(); 427 428 if (authority != null) { 429 sb.append("//").append(authority); 430 } 431 if (path != null) { 432 sb.append(path); 433 } 434 if (query != null) { 435 sb.append('?').append(query); 436 } 437 438 String ssp = sb.toString(); 439 440 if (scheme != null) { 441 sb.insert(0, scheme + ":"); 442 } 443 if (fragment != null) { 444 sb.append('#').append(fragment); 445 } 446 447 String uriString = sb.toString(); 448 449 Uri uri = Uri.parse(uriString); 450 451 // Run these twice to test caching. 452 compareHierarchical( 453 uriString, ssp, uri, scheme, authority, path, query, fragment); 454 compareHierarchical( 455 uriString, ssp, uri, scheme, authority, path, query, fragment); 456 457 // Test rebuilt version. 458 uri = uri.buildUpon().build(); 459 460 // Run these twice to test caching. 461 compareHierarchical( 462 uriString, ssp, uri, scheme, authority, path, query, fragment); 463 compareHierarchical( 464 uriString, ssp, uri, scheme, authority, path, query, fragment); 465 466 // The decoded and encoded versions of the inputs are all the same. 467 // We'll test the actual encoding decoding separately. 468 469 // Test building with encoded versions. 470 Uri built = new Uri.Builder() 471 .scheme(scheme) 472 .encodedAuthority(authority) 473 .encodedPath(path) 474 .encodedQuery(query) 475 .encodedFragment(fragment) 476 .build(); 477 478 compareHierarchical( 479 uriString, ssp, built, scheme, authority, path, query, fragment); 480 compareHierarchical( 481 uriString, ssp, built, scheme, authority, path, query, fragment); 482 483 // Test building with decoded versions. 484 built = new Uri.Builder() 485 .scheme(scheme) 486 .authority(authority) 487 .path(path) 488 .query(query) 489 .fragment(fragment) 490 .build(); 491 492 compareHierarchical( 493 uriString, ssp, built, scheme, authority, path, query, fragment); 494 compareHierarchical( 495 uriString, ssp, built, scheme, authority, path, query, fragment); 496 497 // Rebuild. 498 built = built.buildUpon().build(); 499 500 compareHierarchical( 501 uriString, ssp, built, scheme, authority, path, query, fragment); 502 compareHierarchical( 503 uriString, ssp, built, scheme, authority, path, query, fragment); 504 } 505 506 private static void compareHierarchical(String uriString, String ssp, 507 Uri uri, 508 String scheme, String authority, String path, String query, 509 String fragment) { 510 assertEquals(scheme, uri.getScheme()); 511 assertEquals(authority, uri.getAuthority()); 512 assertEquals(authority, uri.getEncodedAuthority()); 513 assertEquals(path, uri.getPath()); 514 assertEquals(path, uri.getEncodedPath()); 515 assertEquals(query, uri.getQuery()); 516 assertEquals(query, uri.getEncodedQuery()); 517 assertEquals(fragment, uri.getFragment()); 518 assertEquals(fragment, uri.getEncodedFragment()); 519 assertEquals(ssp, uri.getSchemeSpecificPart()); 520 521 if (scheme != null) { 522 assertTrue(uri.isAbsolute()); 523 assertFalse(uri.isRelative()); 524 } else { 525 assertFalse(uri.isAbsolute()); 526 assertTrue(uri.isRelative()); 527 } 528 529 assertFalse(uri.isOpaque()); 530 assertTrue(uri.isHierarchical()); 531 532 assertEquals(uriString, uri.toString()); 533 } 534 535 public void testEmptyToStringNotNull() { 536 assertNotNull(Uri.EMPTY.toString()); 537 } 538 539 @SmallTest 540 public void testParcellingWithoutFragment() { 541 parcelAndUnparcel(Uri.parse("foo:bob%20lee")); 542 parcelAndUnparcel(Uri.fromParts("foo", "bob lee", "fragment")); 543 parcelAndUnparcel(new Uri.Builder() 544 .scheme("http") 545 .authority("crazybob.org") 546 .path("/rss/") 547 .encodedQuery("a=b") 548 .build()); 549 } 550 551 public void testGetQueryParameter() { 552 String nestedUrl = "http://crazybob.org/?a=1&b=2"; 553 Uri uri = Uri.parse("http://test/").buildUpon() 554 .appendQueryParameter("foo", "bar") 555 .appendQueryParameter("nested", nestedUrl).build(); 556 assertEquals(nestedUrl, uri.getQueryParameter("nested")); 557 assertEquals(nestedUrl, uri.getQueryParameters("nested").get(0)); 558 } 559 560 public void testGetQueryParameterWorkaround() { 561 // This was a workaround for a bug where getQueryParameter called 562 // getQuery() instead of getEncodedQuery(). 563 String nestedUrl = "http://crazybob.org/?a=1&b=2"; 564 Uri uri = Uri.parse("http://test/").buildUpon() 565 .appendQueryParameter("foo", "bar") 566 .appendQueryParameter("nested", Uri.encode(nestedUrl)).build(); 567 assertEquals(nestedUrl, Uri.decode(uri.getQueryParameter("nested"))); 568 assertEquals(nestedUrl, 569 Uri.decode(uri.getQueryParameters("nested").get(0))); 570 } 571 572 public void testGetQueryParameterEdgeCases() { 573 Uri uri; 574 575 // key at beginning of URL 576 uri = Uri.parse("http://test/").buildUpon() 577 .appendQueryParameter("key", "a b") 578 .appendQueryParameter("keya", "c d") 579 .appendQueryParameter("bkey", "e f") 580 .build(); 581 assertEquals("a b", uri.getQueryParameter("key")); 582 583 // key in middle of URL 584 uri = Uri.parse("http://test/").buildUpon() 585 .appendQueryParameter("akeyb", "a b") 586 .appendQueryParameter("keya", "c d") 587 .appendQueryParameter("key", "e f") 588 .appendQueryParameter("bkey", "g h") 589 .build(); 590 assertEquals("e f", uri.getQueryParameter("key")); 591 592 // key at end of URL 593 uri = Uri.parse("http://test/").buildUpon() 594 .appendQueryParameter("akeyb", "a b") 595 .appendQueryParameter("keya", "c d") 596 .appendQueryParameter("key", "y z") 597 .build(); 598 assertEquals("y z", uri.getQueryParameter("key")); 599 600 // key is a substring of parameters, but not present 601 uri = Uri.parse("http://test/").buildUpon() 602 .appendQueryParameter("akeyb", "a b") 603 .appendQueryParameter("keya", "c d") 604 .appendQueryParameter("bkey", "e f") 605 .build(); 606 assertNull(uri.getQueryParameter("key")); 607 608 // key is a prefix or suffix of the query 609 uri = Uri.parse("http://test/?qq=foo"); 610 assertNull(uri.getQueryParameter("q")); 611 assertNull(uri.getQueryParameter("oo")); 612 613 // escaped keys 614 uri = Uri.parse("http://www.google.com/?a%20b=foo&c%20d="); 615 assertEquals("foo", uri.getQueryParameter("a b")); 616 assertEquals("", uri.getQueryParameter("c d")); 617 assertNull(uri.getQueryParameter("e f")); 618 assertNull(uri.getQueryParameter("b")); 619 assertNull(uri.getQueryParameter("c")); 620 assertNull(uri.getQueryParameter(" d")); 621 622 // empty values 623 uri = Uri.parse("http://www.google.com/?a=&b=&&c="); 624 assertEquals("", uri.getQueryParameter("a")); 625 assertEquals("", uri.getQueryParameter("b")); 626 assertEquals("", uri.getQueryParameter("c")); 627 } 628 629 public void testGetQueryParameterEmptyKey() { 630 Uri uri = Uri.parse("http://www.google.com/?=b"); 631 assertEquals("b", uri.getQueryParameter("")); 632 } 633 634 public void testGetQueryParameterEmptyKey2() { 635 Uri uri = Uri.parse("http://www.google.com/?a=b&&c=d"); 636 assertEquals("", uri.getQueryParameter("")); 637 } 638 639 public void testGetQueryParameterEmptyKey3() { 640 Uri uri = Uri.parse("http://www.google.com?"); 641 assertEquals("", uri.getQueryParameter("")); 642 } 643 644 public void testGetQueryParameterEmptyKey4() { 645 Uri uri = Uri.parse("http://www.google.com?a=b&"); 646 assertEquals("", uri.getQueryParameter("")); 647 } 648 649 public void testGetQueryParametersEmptyKey() { 650 Uri uri = Uri.parse("http://www.google.com/?=b&"); 651 List<String> values = uri.getQueryParameters(""); 652 assertEquals(2, values.size()); 653 assertEquals("b", values.get(0)); 654 assertEquals("", values.get(1)); 655 } 656 657 public void testGetQueryParametersEmptyKey2() { 658 Uri uri = Uri.parse("http://www.google.com?"); 659 List<String> values = uri.getQueryParameters(""); 660 assertEquals(1, values.size()); 661 assertEquals("", values.get(0)); 662 } 663 664 public void testGetQueryParametersEmptyKey3() { 665 Uri uri = Uri.parse("http://www.google.com/?a=b&&c=d"); 666 List<String> values = uri.getQueryParameters(""); 667 assertEquals(1, values.size()); 668 assertEquals("", values.get(0)); 669 } 670 671 public void testGetQueryParameterNames() { 672 Uri uri = Uri.parse("http://test?a=1"); 673 Set<String> names = uri.getQueryParameterNames(); 674 assertEquals(1, names.size()); 675 assertEquals("a", names.iterator().next()); 676 } 677 678 public void testGetQueryParameterNamesEmptyKey() { 679 Uri uri = Uri.parse("http://www.google.com/?a=x&&c=z"); 680 Set<String> names = uri.getQueryParameterNames(); 681 Iterator<String> iter = names.iterator(); 682 assertEquals(3, names.size()); 683 assertEquals("a", iter.next()); 684 assertEquals("", iter.next()); 685 assertEquals("c", iter.next()); 686 } 687 688 public void testGetQueryParameterNamesEmptyKey2() { 689 Uri uri = Uri.parse("http://www.google.com/?a=x&=d&c=z"); 690 Set<String> names = uri.getQueryParameterNames(); 691 Iterator<String> iter = names.iterator(); 692 assertEquals(3, names.size()); 693 assertEquals("a", iter.next()); 694 assertEquals("", iter.next()); 695 assertEquals("c", iter.next()); 696 } 697 698 public void testGetQueryParameterNamesEmptyValues() { 699 Uri uri = Uri.parse("http://www.google.com/?a=foo&b=&c="); 700 Set<String> names = uri.getQueryParameterNames(); 701 Iterator<String> iter = names.iterator(); 702 assertEquals(3, names.size()); 703 assertEquals("a", iter.next()); 704 assertEquals("b", iter.next()); 705 assertEquals("c", iter.next()); 706 } 707 708 public void testGetQueryParameterNamesEdgeCases() { 709 Uri uri = Uri.parse("http://foo?a=bar&b=bar&c=&&d=baz&e&f&g=buzz&&&a&b=bar&h"); 710 Set<String> names = uri.getQueryParameterNames(); 711 Iterator<String> iter = names.iterator(); 712 assertEquals(9, names.size()); 713 assertEquals("a", iter.next()); 714 assertEquals("b", iter.next()); 715 assertEquals("c", iter.next()); 716 assertEquals("", iter.next()); 717 assertEquals("d", iter.next()); 718 assertEquals("e", iter.next()); 719 assertEquals("f", iter.next()); 720 assertEquals("g", iter.next()); 721 assertEquals("h", iter.next()); 722 } 723 724 public void testGetQueryParameterNamesEscapedKeys() { 725 Uri uri = Uri.parse("http://www.google.com/?a%20b=foo&c%20d="); 726 Set<String> names = uri.getQueryParameterNames(); 727 assertEquals(2, names.size()); 728 Iterator<String> iter = names.iterator(); 729 assertEquals("a b", iter.next()); 730 assertEquals("c d", iter.next()); 731 } 732 733 public void testGetQueryParameterEscapedKeys() { 734 Uri uri = Uri.parse("http://www.google.com/?a%20b=foo&c%20d="); 735 String value = uri.getQueryParameter("a b"); 736 assertEquals("foo", value); 737 } 738 739 public void testClearQueryParameters() { 740 Uri uri = Uri.parse("http://www.google.com/?a=x&b=y&c=z").buildUpon() 741 .clearQuery().appendQueryParameter("foo", "bar").build(); 742 Set<String> names = uri.getQueryParameterNames(); 743 assertEquals(1, names.size()); 744 assertEquals("foo", names.iterator().next()); 745 } 746 747 /** 748 * Query parameters may omit the '='. http://b/3124097 749 */ 750 public void testGetQueryParametersEmptyValue() { 751 assertEquals(Arrays.asList(""), 752 Uri.parse("http://foo/path?abc").getQueryParameters("abc")); 753 assertEquals(Arrays.asList(""), 754 Uri.parse("http://foo/path?foo=bar&abc").getQueryParameters("abc")); 755 assertEquals(Arrays.asList(""), 756 Uri.parse("http://foo/path?abcd=abc&abc").getQueryParameters("abc")); 757 assertEquals(Arrays.asList("a", "", ""), 758 Uri.parse("http://foo/path?abc=a&abc=&abc").getQueryParameters("abc")); 759 assertEquals(Arrays.asList("a", "", ""), 760 Uri.parse("http://foo/path?abc=a&abc=&abc=").getQueryParameters("abc")); 761 } 762 763 // http://code.google.com/p/android/issues/detail?id=21064 764 public void testPlusCharacterInQuery() { 765 assertEquals("d e", Uri.parse("http://a/b?c=d%20e").getQueryParameter("c")); 766 assertEquals("d e", Uri.parse("http://a/b?c=d+e").getQueryParameter("c")); 767 } 768 769 public void testPathPrefixMatch() { 770 // Exact match 771 assertTrue(Uri.parse("content://com.example/path").isPathPrefixMatch( 772 Uri.parse("content://com.example/path/"))); 773 assertTrue(Uri.parse("content://com.example/path").isPathPrefixMatch( 774 Uri.parse("content://com.example/path"))); 775 assertTrue(Uri.parse("content://com.example///path///").isPathPrefixMatch( 776 Uri.parse("content://com.example/path/"))); 777 assertTrue(Uri.parse("content://com.example/path").isPathPrefixMatch( 778 Uri.parse("content://com.example///path///"))); 779 780 // Child match 781 assertTrue(Uri.parse("content://com.example/path/to/child").isPathPrefixMatch( 782 Uri.parse("content://com.example/path/"))); 783 assertTrue(Uri.parse("content://com.example/path/to/child").isPathPrefixMatch( 784 Uri.parse("content://com.example/path"))); 785 786 // Extra parameters 787 assertTrue(Uri.parse("content://com.example/path#fragment").isPathPrefixMatch( 788 Uri.parse("content://com.example/path/"))); 789 assertTrue(Uri.parse("content://com.example/path?q=v").isPathPrefixMatch( 790 Uri.parse("content://com.example/path/"))); 791 assertTrue(Uri.parse("content://com.example/path/?q=v").isPathPrefixMatch( 792 Uri.parse("content://com.example/path/"))); 793 794 // Different path 795 assertFalse(Uri.parse("content://com.example/path").isPathPrefixMatch( 796 Uri.parse("content://com.example/path/deeper/"))); 797 assertFalse(Uri.parse("content://com.example/path2").isPathPrefixMatch( 798 Uri.parse("content://com.example/path"))); 799 800 // Top-level match 801 assertTrue(Uri.parse("content://com.example/path/").isPathPrefixMatch( 802 Uri.parse("content://com.example/"))); 803 assertTrue(Uri.parse("content://com.example/path/").isPathPrefixMatch( 804 Uri.parse("content://com.example"))); 805 806 // Different prefixes 807 assertFalse(Uri.parse("content://com.example/path/").isPathPrefixMatch( 808 Uri.parse("file://com.example/path/"))); 809 assertFalse(Uri.parse("content://com.example/path/").isPathPrefixMatch( 810 Uri.parse("content://org.example/path/"))); 811 812 // Escaping 813 assertTrue(Uri.parse("content://com.example/path path/").isPathPrefixMatch( 814 Uri.parse("content://com.example/path%20path/"))); 815 assertFalse(Uri.parse("content://com.example/path/path").isPathPrefixMatch( 816 Uri.parse("content://com.example/path%2Fpath"))); 817 } 818 819 public void testToSafeString() { 820 checkToSafeString("tel:xxxxxx", "tel:Google"); 821 checkToSafeString("tel:xxxxxxxxxx", "tel:1234567890"); 822 checkToSafeString("tEl:xxx.xxx-xxxx", "tEl:123.456-7890"); 823 824 checkToSafeString("sms:xxxxxx", "sms:123abc"); 825 checkToSafeString("smS:xxx.xxx-xxxx", "smS:123.456-7890"); 826 827 checkToSafeString("smsto:xxxxxx", "smsto:123abc"); 828 checkToSafeString("SMSTo:xxx.xxx-xxxx", "SMSTo:123.456-7890"); 829 830 checkToSafeString("mailto:xxxxxxx@xxxxxxx.xxx", "mailto:android@android.com"); 831 checkToSafeString("Mailto:xxxxxxx@xxxxxxx.xxxxxxxxxx", 832 "Mailto:android@android.com/secret"); 833 834 checkToSafeString("sip:xxxxxxx@xxxxxxx.xxxxxxxx", "sip:android@android.com:1234"); 835 checkToSafeString("sIp:xxxxxxx@xxxxxxx.xxx", "sIp:android@android.com"); 836 837 checkToSafeString("http://www.android.com/...", "http://www.android.com"); 838 checkToSafeString("HTTP://www.android.com/...", "HTTP://www.android.com"); 839 checkToSafeString("http://www.android.com/...", "http://www.android.com/"); 840 checkToSafeString("http://www.android.com/...", "http://www.android.com/secretUrl?param"); 841 checkToSafeString("http://www.android.com/...", 842 "http://user:pwd@www.android.com/secretUrl?param"); 843 checkToSafeString("http://www.android.com/...", 844 "http://user@www.android.com/secretUrl?param"); 845 checkToSafeString("http://www.android.com/...", "http://www.android.com/secretUrl?param"); 846 checkToSafeString("http:///...", "http:///path?param"); 847 checkToSafeString("http:///...", "http://"); 848 checkToSafeString("http://:12345/...", "http://:12345/"); 849 850 checkToSafeString("https://www.android.com/...", "https://www.android.com/secretUrl?param"); 851 checkToSafeString("https://www.android.com:8443/...", 852 "https://user:pwd@www.android.com:8443/secretUrl?param"); 853 checkToSafeString("https://www.android.com/...", "https://user:pwd@www.android.com"); 854 checkToSafeString("Https://www.android.com/...", "Https://user:pwd@www.android.com"); 855 856 checkToSafeString("ftp://ftp.android.com/...", "ftp://ftp.android.com/"); 857 checkToSafeString("ftP://ftp.android.com/...", "ftP://anonymous@ftp.android.com/"); 858 checkToSafeString("ftp://ftp.android.com:2121/...", 859 "ftp://root:love@ftp.android.com:2121/"); 860 861 checkToSafeString("unsupported://ajkakjah/askdha/secret?secret", 862 "unsupported://ajkakjah/askdha/secret?secret"); 863 checkToSafeString("unsupported:ajkakjah/askdha/secret?secret", 864 "unsupported:ajkakjah/askdha/secret?secret"); 865 } 866 867 private void checkToSafeString(String expectedSafeString, String original) { 868 assertEquals(expectedSafeString, Uri.parse(original).toSafeString()); 869 } 870} 871