Changeset 232318 in webkit
- Timestamp:
- May 30, 2018 4:42:36 PM (6 years ago)
- Location:
- trunk
- Files:
-
- 15 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/LayoutTests/ChangeLog
r232317 r232318 1 2018-05-30 Daniel Bates <dabates@apple.com> 2 3 Web Inspector: Annotate Same-Site cookies 4 https://bugs.webkit.org/show_bug.cgi?id=184897 5 <rdar://problem/35178209> 6 7 Reviewed by Brian Burg. 8 9 Update an existing test to ensure we include cookie details in the HTTP Archive (HAR) report. 10 11 * http/tests/inspector/network/har/har-page-expected.txt: 12 * http/tests/inspector/network/har/har-page.html: 13 1 14 2018-05-30 John Wilander <wilander@apple.com> 2 15 -
trunk/LayoutTests/http/tests/inspector/network/har/har-page-expected.txt
r231391 r232318 104 104 "receive": "<filtered>" 105 105 } 106 }, 107 { 108 "pageref": "page_0", 109 "startedDateTime": "<filtered>", 110 "time": "<filtered>", 111 "request": { 112 "method": "GET", 113 "url": "http://127.0.0.1:8000/cookies/resources/cookie-utilities.js", 114 "httpVersion": "<filtered>", 115 "cookies": [], 116 "headers": "<filtered>", 117 "queryString": [], 118 "headersSize": "<filtered>", 119 "bodySize": "<filtered>" 120 }, 121 "response": { 122 "status": 200, 123 "statusText": "OK", 124 "httpVersion": "<filtered>", 125 "cookies": [], 126 "headers": "<filtered>", 127 "content": { 128 "size": "<filtered>", 129 "compression": 0, 130 "mimeType": "application/x-javascript", 131 "text": "<filtered>" 132 }, 133 "redirectURL": "", 134 "headersSize": "<filtered>", 135 "bodySize": "<filtered>" 136 }, 137 "cache": {}, 138 "timings": { 139 "blocked": "<filtered>", 140 "dns": "<filtered>", 141 "connect": "<filtered>", 142 "ssl": -1, 143 "send": "<filtered>", 144 "wait": "<filtered>", 145 "receive": "<filtered>" 146 } 147 }, 148 { 149 "pageref": "page_0", 150 "startedDateTime": "<filtered>", 151 "time": "<filtered>", 152 "request": { 153 "method": "GET", 154 "url": "http://127.0.0.1:8000/cookies/resources/setCookies.cgi", 155 "httpVersion": "<filtered>", 156 "cookies": [], 157 "headers": "<filtered>", 158 "queryString": [], 159 "headersSize": "<filtered>", 160 "bodySize": "<filtered>" 161 }, 162 "response": { 163 "status": 200, 164 "statusText": "OK", 165 "httpVersion": "<filtered>", 166 "cookies": [ 167 { 168 "name": "simple", 169 "value": "simple", 170 "expires": "", 171 "httpOnly": false, 172 "secure": false 173 } 174 ], 175 "headers": "<filtered>", 176 "content": { 177 "size": "<filtered>", 178 "compression": 0, 179 "mimeType": "text/plain" 180 }, 181 "redirectURL": "", 182 "headersSize": "<filtered>", 183 "bodySize": "<filtered>" 184 }, 185 "cache": {}, 186 "timings": { 187 "blocked": "<filtered>", 188 "dns": "<filtered>", 189 "connect": "<filtered>", 190 "ssl": -1, 191 "send": "<filtered>", 192 "wait": "<filtered>", 193 "receive": "<filtered>" 194 } 195 }, 196 { 197 "pageref": "page_0", 198 "startedDateTime": "<filtered>", 199 "time": "<filtered>", 200 "request": { 201 "method": "GET", 202 "url": "http://127.0.0.1:8000/cookies/resources/setCookies.cgi", 203 "httpVersion": "<filtered>", 204 "cookies": [ 205 { 206 "name": "simple", 207 "value": "simple" 208 } 209 ], 210 "headers": "<filtered>", 211 "queryString": [], 212 "headersSize": "<filtered>", 213 "bodySize": "<filtered>" 214 }, 215 "response": { 216 "status": 200, 217 "statusText": "OK", 218 "httpVersion": "<filtered>", 219 "cookies": [ 220 { 221 "name": "path", 222 "value": "path", 223 "path": "/A/B/C", 224 "expires": "", 225 "httpOnly": false, 226 "secure": false 227 } 228 ], 229 "headers": "<filtered>", 230 "content": { 231 "size": "<filtered>", 232 "compression": 0, 233 "mimeType": "text/plain" 234 }, 235 "redirectURL": "", 236 "headersSize": "<filtered>", 237 "bodySize": "<filtered>" 238 }, 239 "cache": {}, 240 "timings": { 241 "blocked": "<filtered>", 242 "dns": "<filtered>", 243 "connect": "<filtered>", 244 "ssl": -1, 245 "send": "<filtered>", 246 "wait": "<filtered>", 247 "receive": "<filtered>" 248 } 249 }, 250 { 251 "pageref": "page_0", 252 "startedDateTime": "<filtered>", 253 "time": "<filtered>", 254 "request": { 255 "method": "GET", 256 "url": "http://127.0.0.1:8000/cookies/resources/setCookies.cgi", 257 "httpVersion": "<filtered>", 258 "cookies": [ 259 { 260 "name": "simple", 261 "value": "simple" 262 } 263 ], 264 "headers": "<filtered>", 265 "queryString": [], 266 "headersSize": "<filtered>", 267 "bodySize": "<filtered>" 268 }, 269 "response": { 270 "status": 200, 271 "statusText": "OK", 272 "httpVersion": "<filtered>", 273 "cookies": [ 274 { 275 "name": "secure", 276 "value": "secure", 277 "expires": "", 278 "httpOnly": false, 279 "secure": true 280 } 281 ], 282 "headers": "<filtered>", 283 "content": { 284 "size": "<filtered>", 285 "compression": 0, 286 "mimeType": "text/plain" 287 }, 288 "redirectURL": "", 289 "headersSize": "<filtered>", 290 "bodySize": "<filtered>" 291 }, 292 "cache": {}, 293 "timings": { 294 "blocked": "<filtered>", 295 "dns": "<filtered>", 296 "connect": "<filtered>", 297 "ssl": -1, 298 "send": "<filtered>", 299 "wait": "<filtered>", 300 "receive": "<filtered>" 301 } 302 }, 303 { 304 "pageref": "page_0", 305 "startedDateTime": "<filtered>", 306 "time": "<filtered>", 307 "request": { 308 "method": "GET", 309 "url": "http://127.0.0.1:8000/cookies/resources/setCookies.cgi", 310 "httpVersion": "<filtered>", 311 "cookies": [ 312 { 313 "name": "simple", 314 "value": "simple" 315 } 316 ], 317 "headers": "<filtered>", 318 "queryString": [], 319 "headersSize": "<filtered>", 320 "bodySize": "<filtered>" 321 }, 322 "response": { 323 "status": 200, 324 "statusText": "OK", 325 "httpVersion": "<filtered>", 326 "cookies": [ 327 { 328 "name": "secure-and-http-only", 329 "value": "secure-and-http-only", 330 "expires": "", 331 "httpOnly": true, 332 "secure": true 333 } 334 ], 335 "headers": "<filtered>", 336 "content": { 337 "size": "<filtered>", 338 "compression": 0, 339 "mimeType": "text/plain" 340 }, 341 "redirectURL": "", 342 "headersSize": "<filtered>", 343 "bodySize": "<filtered>" 344 }, 345 "cache": {}, 346 "timings": { 347 "blocked": "<filtered>", 348 "dns": "<filtered>", 349 "connect": "<filtered>", 350 "ssl": -1, 351 "send": "<filtered>", 352 "wait": "<filtered>", 353 "receive": "<filtered>" 354 } 355 }, 356 { 357 "pageref": "page_0", 358 "startedDateTime": "<filtered>", 359 "time": "<filtered>", 360 "request": { 361 "method": "GET", 362 "url": "http://127.0.0.1:8000/cookies/resources/setCookies.cgi", 363 "httpVersion": "<filtered>", 364 "cookies": [ 365 { 366 "name": "simple", 367 "value": "simple" 368 } 369 ], 370 "headers": "<filtered>", 371 "queryString": [], 372 "headersSize": "<filtered>", 373 "bodySize": "<filtered>" 374 }, 375 "response": { 376 "status": 200, 377 "statusText": "OK", 378 "httpVersion": "<filtered>", 379 "cookies": [ 380 { 381 "name": "with-expiration", 382 "value": "with-expiration", 383 "expires": "5000-01-04T08:00:00.000Z", 384 "httpOnly": false, 385 "secure": false 386 } 387 ], 388 "headers": "<filtered>", 389 "content": { 390 "size": "<filtered>", 391 "compression": 0, 392 "mimeType": "text/plain" 393 }, 394 "redirectURL": "", 395 "headersSize": "<filtered>", 396 "bodySize": "<filtered>" 397 }, 398 "cache": {}, 399 "timings": { 400 "blocked": "<filtered>", 401 "dns": "<filtered>", 402 "connect": "<filtered>", 403 "ssl": -1, 404 "send": "<filtered>", 405 "wait": "<filtered>", 406 "receive": "<filtered>" 407 } 408 }, 409 { 410 "pageref": "page_0", 411 "startedDateTime": "<filtered>", 412 "time": "<filtered>", 413 "request": { 414 "method": "GET", 415 "url": "http://127.0.0.1:8000/cookies/resources/setCookies.cgi", 416 "httpVersion": "<filtered>", 417 "cookies": [ 418 { 419 "name": "simple", 420 "value": "simple" 421 }, 422 { 423 "name": "with-expiration", 424 "value": "with-expiration" 425 } 426 ], 427 "headers": "<filtered>", 428 "queryString": [], 429 "headersSize": "<filtered>", 430 "bodySize": "<filtered>" 431 }, 432 "response": { 433 "status": 200, 434 "statusText": "OK", 435 "httpVersion": "<filtered>", 436 "cookies": [ 437 { 438 "name": "http-only", 439 "value": "http-only", 440 "expires": "", 441 "httpOnly": true, 442 "secure": false 443 } 444 ], 445 "headers": "<filtered>", 446 "content": { 447 "size": "<filtered>", 448 "compression": 0, 449 "mimeType": "text/plain" 450 }, 451 "redirectURL": "", 452 "headersSize": "<filtered>", 453 "bodySize": "<filtered>" 454 }, 455 "cache": {}, 456 "timings": { 457 "blocked": "<filtered>", 458 "dns": "<filtered>", 459 "connect": "<filtered>", 460 "ssl": -1, 461 "send": "<filtered>", 462 "wait": "<filtered>", 463 "receive": "<filtered>" 464 } 465 }, 466 { 467 "pageref": "page_0", 468 "startedDateTime": "<filtered>", 469 "time": "<filtered>", 470 "request": { 471 "method": "GET", 472 "url": "http://127.0.0.1:8000/cookies/resources/setCookies.cgi", 473 "httpVersion": "<filtered>", 474 "cookies": [ 475 { 476 "name": "http-only", 477 "value": "http-only" 478 }, 479 { 480 "name": "simple", 481 "value": "simple" 482 }, 483 { 484 "name": "with-expiration", 485 "value": "with-expiration" 486 } 487 ], 488 "headers": "<filtered>", 489 "queryString": [], 490 "headersSize": "<filtered>", 491 "bodySize": "<filtered>" 492 }, 493 "response": { 494 "status": 200, 495 "statusText": "OK", 496 "httpVersion": "<filtered>", 497 "cookies": [ 498 { 499 "name": "same-site-strict", 500 "value": "same-site-strict", 501 "path": "/", 502 "expires": "", 503 "httpOnly": false, 504 "secure": false, 505 "sameSite": "Strict" 506 } 507 ], 508 "headers": "<filtered>", 509 "content": { 510 "size": "<filtered>", 511 "compression": 0, 512 "mimeType": "text/plain" 513 }, 514 "redirectURL": "", 515 "headersSize": "<filtered>", 516 "bodySize": "<filtered>" 517 }, 518 "cache": {}, 519 "timings": { 520 "blocked": "<filtered>", 521 "dns": "<filtered>", 522 "connect": "<filtered>", 523 "ssl": -1, 524 "send": "<filtered>", 525 "wait": "<filtered>", 526 "receive": "<filtered>" 527 } 528 }, 529 { 530 "pageref": "page_0", 531 "startedDateTime": "<filtered>", 532 "time": "<filtered>", 533 "request": { 534 "method": "GET", 535 "url": "http://127.0.0.1:8000/cookies/resources/setCookies.cgi", 536 "httpVersion": "<filtered>", 537 "cookies": [ 538 { 539 "name": "http-only", 540 "value": "http-only" 541 }, 542 { 543 "name": "simple", 544 "value": "simple" 545 }, 546 { 547 "name": "with-expiration", 548 "value": "with-expiration" 549 }, 550 { 551 "name": "same-site-strict", 552 "value": "same-site-strict" 553 } 554 ], 555 "headers": "<filtered>", 556 "queryString": [], 557 "headersSize": "<filtered>", 558 "bodySize": "<filtered>" 559 }, 560 "response": { 561 "status": 200, 562 "statusText": "OK", 563 "httpVersion": "<filtered>", 564 "cookies": [ 565 { 566 "name": "same-site-implicit-strict", 567 "value": "same-site-implicit-strict", 568 "path": "/", 569 "expires": "", 570 "httpOnly": false, 571 "secure": false, 572 "sameSite": "Strict" 573 } 574 ], 575 "headers": "<filtered>", 576 "content": { 577 "size": "<filtered>", 578 "compression": 0, 579 "mimeType": "text/plain" 580 }, 581 "redirectURL": "", 582 "headersSize": "<filtered>", 583 "bodySize": "<filtered>" 584 }, 585 "cache": {}, 586 "timings": { 587 "blocked": "<filtered>", 588 "dns": "<filtered>", 589 "connect": "<filtered>", 590 "ssl": -1, 591 "send": "<filtered>", 592 "wait": "<filtered>", 593 "receive": "<filtered>" 594 } 595 }, 596 { 597 "pageref": "page_0", 598 "startedDateTime": "<filtered>", 599 "time": "<filtered>", 600 "request": { 601 "method": "GET", 602 "url": "http://127.0.0.1:8000/cookies/resources/setCookies.cgi", 603 "httpVersion": "<filtered>", 604 "cookies": [ 605 { 606 "name": "http-only", 607 "value": "http-only" 608 }, 609 { 610 "name": "simple", 611 "value": "simple" 612 }, 613 { 614 "name": "with-expiration", 615 "value": "with-expiration" 616 }, 617 { 618 "name": "same-site-implicit-strict", 619 "value": "same-site-implicit-strict" 620 }, 621 { 622 "name": "same-site-strict", 623 "value": "same-site-strict" 624 } 625 ], 626 "headers": "<filtered>", 627 "queryString": [], 628 "headersSize": "<filtered>", 629 "bodySize": "<filtered>" 630 }, 631 "response": { 632 "status": 200, 633 "statusText": "OK", 634 "httpVersion": "<filtered>", 635 "cookies": [ 636 { 637 "name": "same-site-strict-because-invalid-SameSite-value", 638 "value": "same-site-strict-because-invalid-SameSite-value", 639 "path": "/", 640 "expires": "", 641 "httpOnly": false, 642 "secure": false, 643 "sameSite": "Strict" 644 } 645 ], 646 "headers": "<filtered>", 647 "content": { 648 "size": "<filtered>", 649 "compression": 0, 650 "mimeType": "text/plain" 651 }, 652 "redirectURL": "", 653 "headersSize": "<filtered>", 654 "bodySize": "<filtered>" 655 }, 656 "cache": {}, 657 "timings": { 658 "blocked": "<filtered>", 659 "dns": "<filtered>", 660 "connect": "<filtered>", 661 "ssl": -1, 662 "send": "<filtered>", 663 "wait": "<filtered>", 664 "receive": "<filtered>" 665 } 666 }, 667 { 668 "pageref": "page_0", 669 "startedDateTime": "<filtered>", 670 "time": "<filtered>", 671 "request": { 672 "method": "GET", 673 "url": "http://127.0.0.1:8000/cookies/resources/setCookies.cgi", 674 "httpVersion": "<filtered>", 675 "cookies": [ 676 { 677 "name": "http-only", 678 "value": "http-only" 679 }, 680 { 681 "name": "simple", 682 "value": "simple" 683 }, 684 { 685 "name": "with-expiration", 686 "value": "with-expiration" 687 }, 688 { 689 "name": "same-site-implicit-strict", 690 "value": "same-site-implicit-strict" 691 }, 692 { 693 "name": "same-site-strict", 694 "value": "same-site-strict" 695 }, 696 { 697 "name": "same-site-strict-because-invalid-SameSite-value", 698 "value": "same-site-strict-because-invalid-SameSite-value" 699 } 700 ], 701 "headers": "<filtered>", 702 "queryString": [], 703 "headersSize": "<filtered>", 704 "bodySize": "<filtered>" 705 }, 706 "response": { 707 "status": 200, 708 "statusText": "OK", 709 "httpVersion": "<filtered>", 710 "cookies": [ 711 { 712 "name": "same-site-lax", 713 "value": "same-site-lax", 714 "path": "/", 715 "expires": "", 716 "httpOnly": false, 717 "secure": false, 718 "sameSite": "Lax" 719 } 720 ], 721 "headers": "<filtered>", 722 "content": { 723 "size": "<filtered>", 724 "compression": 0, 725 "mimeType": "text/plain" 726 }, 727 "redirectURL": "", 728 "headersSize": "<filtered>", 729 "bodySize": "<filtered>" 730 }, 731 "cache": {}, 732 "timings": { 733 "blocked": "<filtered>", 734 "dns": "<filtered>", 735 "connect": "<filtered>", 736 "ssl": -1, 737 "send": "<filtered>", 738 "wait": "<filtered>", 739 "receive": "<filtered>" 740 } 106 741 } 107 742 ] -
trunk/LayoutTests/http/tests/inspector/network/har/har-page.html
r231391 r232318 4 4 <meta charset="utf-8"> 5 5 <script src="../../resources/inspector-test.js"></script> 6 <script src="../../../cookies/resources/cookie-utilities.js"></script> 6 7 <script> 7 8 function test() … … 50 51 } 51 52 53 // Sort cookies by name to make cookie order deterministic between test runs. 54 if (key === "cookies") 55 value.sort((a, b) => { return a.name - b.name; }); 56 52 57 // Since cache may or may not be used, timing data may be variable. 53 58 // NOTE: SSL should always be -1 for this test case. … … 78 83 InspectorTest.reloadPage({ignoreCache: true}); 79 84 await InspectorTest.awaitEvent("LoadComplete"); 85 InspectorTest.evaluateInPage("setup()"); 86 await InspectorTest.awaitEvent("SetupComplete"); 80 87 81 88 let resources = [WI.frameResourceManager.mainFrame.mainResource, ...WI.frameResourceManager.mainFrame.resourceCollection]; 82 89 let har = await WI.HARBuilder.buildArchive(resources); 83 90 InspectorTest.json(har, HARJSONFilter); 91 InspectorTest.evaluateInPage("cleanup()"); 92 await InspectorTest.awaitEvent("CleanComplete"); 84 93 } 85 94 }); … … 92 101 <p>HAR Page Test.</p> 93 102 <script> 103 async function setup() 104 { 105 await resetCookies(); 106 await setCookie("simple", "simple"); 107 await setCookie("path", "path", {"path": "/A/B/C"}); // This cookie will not be sent in subsequent requests from this page. 108 109 // Secure cookies will only be sent in subsequent requests from this page if the page was served over HTTPS. 110 await setCookie("secure", "secure", {"secure": null}); 111 await setCookie("secure-and-http-only", "secure-and-http-only", {"secure": null, "HttpOnly": null}); 112 113 await setCookie("with-expiration", "with-expiration", {"Expires": new Date("01/04/5000").toGMTString()}); 114 await setCookie("http-only", "http-only", {"HttpOnly": null}); 115 await setCookie("same-site-strict", "same-site-strict", {"SameSite": "Strict", "path": "/"}); 116 await setCookie("same-site-implicit-strict", "same-site-implicit-strict", {"SameSite": null, "path": "/"}); 117 await setCookie("same-site-strict-because-invalid-SameSite-value", "same-site-strict-because-invalid-SameSite-value", {"SameSite": "invalid", "path": "/"}); 118 await setCookie("same-site-lax", "same-site-lax", {"SameSite": "Lax", "path": "/"}); 119 TestPage.dispatchEventToFrontend("SetupComplete"); 120 } 121 122 async function cleanup() 123 { 124 await resetCookies(); 125 TestPage.dispatchEventToFrontend("CleanComplete"); 126 } 127 94 128 window.addEventListener("load", () => { 95 129 TestPage.dispatchEventToFrontend("LoadComplete"); -
trunk/Source/JavaScriptCore/ChangeLog
r232314 r232318 1 2018-05-30 Daniel Bates <dabates@apple.com> 2 3 Web Inspector: Annotate Same-Site cookies 4 https://bugs.webkit.org/show_bug.cgi?id=184897 5 <rdar://problem/35178209> 6 7 Reviewed by Brian Burg. 8 9 Update protocol to include cookie Same-Site policy. 10 11 * inspector/protocol/Page.json: 12 1 13 2018-05-29 Keith Miller <keith_miller@apple.com> 2 14 -
trunk/Source/JavaScriptCore/inspector/protocol/Page.json
r231881 r232318 15 15 "enum": ["Viewport", "Page"], 16 16 "description": "Coordinate system used by supplied coordinates." 17 }, 18 { 19 "id": "CookieSameSitePolicy", 20 "type": "string", 21 "enum": ["None", "Lax", "Strict"], 22 "description": "Same-Site policy of a cookie." 17 23 }, 18 24 { … … 77 83 { "name": "httpOnly", "type": "boolean", "description": "True if cookie is http-only." }, 78 84 { "name": "secure", "type": "boolean", "description": "True if cookie is secure." }, 79 { "name": "session", "type": "boolean", "description": "True in case of session cookie." } 85 { "name": "session", "type": "boolean", "description": "True in case of session cookie." }, 86 { "name": "sameSite", "$ref": "CookieSameSitePolicy", "description": "Cookie Same-Site policy." } 80 87 ] 81 88 } -
trunk/Source/WebCore/ChangeLog
r232316 r232318 1 2018-05-30 Daniel Bates <dabates@apple.com> 2 3 Web Inspector: Annotate Same-Site cookies 4 https://bugs.webkit.org/show_bug.cgi?id=184897 5 <rdar://problem/35178209> 6 7 Reviewed by Brian Burg. 8 9 Store and retrieve the Same-Site cookie policy from CFNetwork. 10 11 * inspector/agents/InspectorPageAgent.cpp: 12 (WebCore::cookieSameSitePolicyJSON): Added. 13 (WebCore::buildObjectForCookie): Modified to include cookie Same-Site policy. 14 * platform/Cookie.h: 15 (WebCore::Cookie::encode const): Encode Same-Site policy. 16 (WebCore::Cookie::decode): Decode Same-Site policy. 17 * platform/network/cocoa/CookieCocoa.mm: 18 (WebCore::portStringFromVector): 19 (WebCore::coreSameSitePolicy): 20 (WebCore::nsSameSitePolicy): 21 (WebCore::Cookie::operator NSHTTPCookie * _Nullable const): 22 (WebCore::Cookie::operator NSHTTPCookie * const): Deleted. 23 1 24 2018-05-30 Daniel Bates <dabates@apple.com> 2 25 -
trunk/Source/WebCore/inspector/agents/InspectorPageAgent.cpp
r232278 r232318 337 337 } 338 338 339 static Inspector::Protocol::Page::CookieSameSitePolicy cookieSameSitePolicyJSON(Cookie::SameSitePolicy policy) 340 { 341 switch (policy) { 342 case Cookie::SameSitePolicy::None: 343 return Inspector::Protocol::Page::CookieSameSitePolicy::None; 344 case Cookie::SameSitePolicy::Lax: 345 return Inspector::Protocol::Page::CookieSameSitePolicy::Lax; 346 case Cookie::SameSitePolicy::Strict: 347 return Inspector::Protocol::Page::CookieSameSitePolicy::Strict; 348 } 349 ASSERT_NOT_REACHED(); 350 return Inspector::Protocol::Page::CookieSameSitePolicy::None; 351 } 352 339 353 static Ref<Inspector::Protocol::Page::Cookie> buildObjectForCookie(const Cookie& cookie) 340 354 { … … 349 363 .setSecure(cookie.secure) 350 364 .setSession(cookie.session) 365 .setSameSite(cookieSameSitePolicyJSON(cookie.sameSite)) 351 366 .release(); 352 367 } -
trunk/Source/WebCore/platform/Cookie.h
r231859 r232318 1 1 /* 2 2 * Copyright (C) 2009 Joseph Pecoraro. All rights reserved. 3 * Copyright (C) 2017 Apple Inc. All rights reserved.3 * Copyright (C) 2017-2018 Apple Inc. All rights reserved. 4 4 * 5 5 * Redistribution and use in source and binary forms, with or without … … 28 28 29 29 #include "URL.h" 30 #include <wtf/EnumTraits.h> 30 31 #include <wtf/text/StringHash.h> 31 32 #include <wtf/text/WTFString.h> … … 86 87 URL commentURL; 87 88 Vector<uint16_t> ports; 89 90 enum class SameSitePolicy { None, Lax, Strict }; 91 SameSitePolicy sameSite { SameSitePolicy::None }; 88 92 }; 89 93 … … 116 120 encoder << commentURL; 117 121 encoder << ports; 122 encoder << sameSite; 118 123 } 119 124 … … 146 151 if (!decoder.decode(cookie.ports)) 147 152 return std::nullopt; 153 if (!decoder.decode(cookie.sameSite)) 154 return std::nullopt; 148 155 return cookie; 149 156 } … … 161 168 static bool isDeletedValue(const WebCore::Cookie& slot) { return slot.name.isHashTableDeletedValue(); } 162 169 }; 170 template<> struct EnumTraits<WebCore::Cookie::SameSitePolicy> { 171 using values = EnumValues< 172 WebCore::Cookie::SameSitePolicy, 173 WebCore::Cookie::SameSitePolicy::None, 174 WebCore::Cookie::SameSitePolicy::Lax, 175 WebCore::Cookie::SameSitePolicy::Strict 176 >; 177 }; 163 178 } -
trunk/Source/WebCore/platform/network/cocoa/CookieCocoa.mm
r232191 r232318 27 27 #import "Cookie.h" 28 28 29 // FIXME: Remove NS_ASSUME_NONNULL_BEGIN/END and all _Nullable annotations once we remove the NSHTTPCookie forward declaration below. 30 NS_ASSUME_NONNULL_BEGIN 31 32 #if (PLATFORM(MAC) && __MAC_OS_X_VERSION_MIN_REQUIRED >= 101400 && __MAC_OS_X_VERSION_MAX_ALLOWED < 101500) || (PLATFORM(IOS) && __IPHONE_OS_VERSION_MIN_REQUIRED >= 120000 && __IPHONE_OS_VERSION_MAX_ALLOWED < 130000) 33 typedef NSString * NSHTTPCookieStringPolicy; 34 @interface NSHTTPCookie (Staging) 35 @property (nullable, readonly, copy) NSHTTPCookieStringPolicy sameSitePolicy; 36 @end 37 38 static NSString * const NSHTTPCookieSameSiteLax = @"lax"; 39 static NSString * const NSHTTPCookieSameSiteStrict = @"strict"; 40 #endif 41 29 42 namespace WebCore { 30 43 … … 40 53 } 41 54 42 static NSString * portStringFromVector(const Vector<uint16_t>& ports)55 static NSString * _Nullable portStringFromVector(const Vector<uint16_t>& ports) 43 56 { 44 57 if (ports.isEmpty()) … … 71 84 return 0; 72 85 } 86 87 #if (PLATFORM(MAC) && __MAC_OS_X_VERSION_MIN_REQUIRED >= 101400) || (PLATFORM(IOS) && __IPHONE_OS_VERSION_MIN_REQUIRED >= 120000) 88 static Cookie::SameSitePolicy coreSameSitePolicy(NSHTTPCookieStringPolicy _Nullable policy) 89 { 90 if (!policy) 91 return Cookie::SameSitePolicy::None; 92 if ([policy isEqualToString:NSHTTPCookieSameSiteLax]) 93 return Cookie::SameSitePolicy::Lax; 94 if ([policy isEqualToString:NSHTTPCookieSameSiteStrict]) 95 return Cookie::SameSitePolicy::Strict; 96 ASSERT_NOT_REACHED(); 97 return Cookie::SameSitePolicy::None; 98 } 99 100 static NSHTTPCookieStringPolicy _Nullable nsSameSitePolicy(Cookie::SameSitePolicy policy) 101 { 102 switch (policy) { 103 case Cookie::SameSitePolicy::None: 104 return nil; 105 case Cookie::SameSitePolicy::Lax: 106 return NSHTTPCookieSameSiteLax; 107 case Cookie::SameSitePolicy::Strict: 108 return NSHTTPCookieSameSiteStrict; 109 } 110 } 111 #endif 73 112 74 113 Cookie::Cookie(NSHTTPCookie *cookie) … … 86 125 , ports { portVectorFromList(cookie.portList) } 87 126 { 88 } 89 90 Cookie::operator NSHTTPCookie *() const 127 #if (PLATFORM(MAC) && __MAC_OS_X_VERSION_MIN_REQUIRED >= 101400) || (PLATFORM(IOS) && __IPHONE_OS_VERSION_MIN_REQUIRED >= 120000) 128 if ([cookie respondsToSelector:@selector(sameSitePolicy)]) 129 sameSite = coreSameSitePolicy(cookie.sameSitePolicy); 130 #endif 131 } 132 133 Cookie::operator NSHTTPCookie * _Nullable () const 91 134 { 92 135 if (isNull()) 93 136 return nil; 94 137 95 NSMutableDictionary *properties = [NSMutableDictionary dictionaryWithCapacity:1 3];138 NSMutableDictionary *properties = [NSMutableDictionary dictionaryWithCapacity:14]; 96 139 97 140 if (!comment.isNull()) … … 134 177 if (httpOnly) 135 178 [properties setObject:@YES forKey:@"HttpOnly"]; 179 180 #if (PLATFORM(MAC) && __MAC_OS_X_VERSION_MIN_REQUIRED >= 101400) || (PLATFORM(IOS) && __IPHONE_OS_VERSION_MIN_REQUIRED >= 120000) 181 if (auto* sameSitePolicy = nsSameSitePolicy(sameSite)) 182 [properties setObject:sameSitePolicy forKey:@"SameSite"]; 183 #endif 136 184 137 185 [properties setObject:@"1" forKey:NSHTTPCookieVersion]; … … 157 205 } 158 206 207 NS_ASSUME_NONNULL_END 208 159 209 } // namespace WebCore -
trunk/Source/WebInspectorUI/ChangeLog
r232189 r232318 1 2018-05-30 Daniel Bates <dabates@apple.com> 2 3 Web Inspector: Annotate Same-Site cookies 4 https://bugs.webkit.org/show_bug.cgi?id=184897 5 <rdar://problem/35178209> 6 7 Reviewed by Brian Burg. 8 9 Add a new column for the value of the Same-Site cookie attribute to the resource cookie content 10 view (shown for a resource under the Network tab) and cookie storage content view (shown under 11 the Storage tab). 12 13 The SameSite column in the resource cookie content view reflects the parsing of the Same-Site 14 attribute from the HTTP response by Web Inspector. This parsing is materially consistent with 15 the parsing of the SameSite atttribute in CFNetwork. The Same-Site column in the cookie storage 16 content view reflects the Same-Site cookie policy associated with the cookies provided by the 17 network stack, if supported. This column will be blank on systems whose network stack does not 18 support Same-Site cookies (e.g libsoup). 19 20 * Localizations/en.lproj/localizedStrings.js: 21 * UserInterface/Controllers/HARBuilder.js: 22 (WI.HARBuilder.cookies): 23 * UserInterface/Models/Cookie.js: 24 (WI.Cookie): 25 (WI.Cookie.displayNameForSameSiteType): 26 (WI.Cookie.parseSameSiteAttributeValue): 27 (WI.Cookie.parseSetCookieResponseHeader): 28 * UserInterface/Views/CookieStorageContentView.js: 29 (WI.CookieStorageContentView.prototype._rebuildTable): 30 (WI.CookieStorageContentView.prototype._sortDataGrid): 31 * UserInterface/Views/ResourceCookiesContentView.js: 32 (WI.ResourceCookiesContentView.prototype.tablePopulateCell): 33 (WI.ResourceCookiesContentView.prototype._generateSortComparator): 34 (WI.ResourceCookiesContentView.prototype._refreshResponseCookiesSection): 35 1 36 2018-05-25 Matt Baker <mattbaker@apple.com> 2 37 -
trunk/Source/WebInspectorUI/Localizations/en.lproj/localizedStrings.js
r231981 r232318 812 812 localizedStrings["Role"] = "Role"; 813 813 localizedStrings["Rule"] = "Rule"; 814 localizedStrings["Same-Site"] = "Same-Site"; 814 815 localizedStrings["Samples"] = "Samples"; 815 816 localizedStrings["Save File"] = "Save File"; -
trunk/Source/WebInspectorUI/UserInterface/Controllers/HARBuilder.js
r224357 r232318 1 1 /* 2 * Copyright (C) 2017 Apple Inc. All rights reserved.2 * Copyright (C) 2017-2018 Apple Inc. All rights reserved. 3 3 * 4 4 * Redistribution and use in source and binary forms, with or without … … 178 178 json.httpOnly = cookie.httpOnly; 179 179 json.secure = cookie.secure; 180 if (cookie.sameSite !== WI.Cookie.SameSiteType.None) 181 json.sameSite = cookie.sameSite; 180 182 } 181 183 -
trunk/Source/WebInspectorUI/UserInterface/Models/Cookie.js
r223856 r232318 26 26 WI.Cookie = class Cookie 27 27 { 28 constructor(type, name, value, raw, expires, maxAge, path, domain, secure, httpOnly )28 constructor(type, name, value, raw, expires, maxAge, path, domain, secure, httpOnly, sameSite) 29 29 { 30 30 console.assert(Object.values(WI.Cookie.Type).includes(type)); … … 38 38 console.assert(!secure || typeof secure === "boolean"); 39 39 console.assert(!httpOnly || typeof httpOnly === "boolean"); 40 console.assert(!sameSite || Object.values(WI.Cookie.SameSiteType).includes(sameSite)); 40 41 41 42 this.type = type; … … 51 52 this.secure = secure || false; 52 53 this.httpOnly = httpOnly || false; 54 this.sameSite = sameSite || WI.Cookie.SameSiteType.None; 53 55 } 54 56 } … … 100 102 } 101 103 104 static displayNameForSameSiteType(sameSiteType) 105 { 106 switch (sameSiteType) { 107 case WI.Cookie.SameSiteType.None: 108 return WI.unlocalizedString("None"); 109 case WI.Cookie.SameSiteType.Lax: 110 return WI.unlocalizedString("Lax"); 111 case WI.Cookie.SameSiteType.Strict: 112 return WI.unlocalizedString("Strict"); 113 default: 114 console.error("Invalid SameSite type", sameSiteType); 115 return sameSiteType; 116 } 117 } 118 119 // Derived from <https://tools.ietf.org/html/draft-west-first-party-cookies-06#section-3.2>. 120 static parseSameSiteAttributeValue(attributeValue) 121 { 122 if (!attributeValue) 123 return WI.Cookie.SameSiteType.Strict; 124 switch (attributeValue.toLowerCase()) { 125 case "lax": 126 return WI.Cookie.SameSiteType.Lax; 127 case "strict": 128 default: 129 return WI.Cookie.SameSiteType.Strict; 130 } 131 } 132 102 133 static parseSetCookieResponseHeader(header) 103 134 { … … 123 154 let secure = false; 124 155 let httpOnly = false; 156 let sameSite = WI.Cookie.SameSiteType.None; 125 157 126 158 // Parse Attributes … … 172 204 httpOnly = true; 173 205 break; 206 case "samesite": 207 sameSite = WI.Cookie.parseSameSiteAttributeValue(attributeValue); 208 break; 174 209 default: 175 210 console.warn("Unknown Cookie attribute:", attribute); … … 178 213 } 179 214 180 return new WI.Cookie(WI.Cookie.Type.Response, name, value, header, expires, maxAge, path, domain, secure, httpOnly );215 return new WI.Cookie(WI.Cookie.Type.Response, name, value, header, expires, maxAge, path, domain, secure, httpOnly, sameSite); 181 216 } 182 217 } … … 186 221 Response: "response", 187 222 }; 223 224 // Keep these in sync with the "CookieSameSitePolicy" enum defined by the "Page" domain. 225 WI.Cookie.SameSiteType = { 226 None: "None", 227 Lax: "Lax", 228 Strict: "Strict", 229 }; -
trunk/Source/WebInspectorUI/UserInterface/Views/CookieStorageContentView.js
r231391 r232318 1 1 /* 2 * Copyright (C) 2013, 2015 Apple Inc. All rights reserved.2 * Copyright (C) 2013, 2015, 2018 Apple Inc. All rights reserved. 3 3 * 4 4 * Redistribution and use in source and binary forms, with or without … … 74 74 // FIXME <https://webkit.org/b/151400>: If there are no cookies, add placeholder explanatory text. 75 75 if (!this._dataGrid) { 76 var columns = {name: {}, value: {}, domain: {}, path: {}, expires: {}, size: {}, http: {}, secure: {} };76 var columns = {name: {}, value: {}, domain: {}, path: {}, expires: {}, size: {}, http: {}, secure: {}, sameSite: {} }; 77 77 78 78 columns.name.title = WI.UIString("Name"); … … 88 88 columns.domain.title = WI.UIString("Domain"); 89 89 columns.domain.sortable = true; 90 columns.domain.width = " 7%";90 columns.domain.width = "6%"; 91 91 92 92 columns.path.title = WI.UIString("Path"); 93 93 columns.path.sortable = true; 94 columns.path.width = " 7%";94 columns.path.width = "6%"; 95 95 96 96 columns.expires.title = WI.UIString("Expires"); 97 97 columns.expires.sortable = true; 98 columns.expires.width = " 7%";98 columns.expires.width = "6%"; 99 99 100 100 columns.size.title = WI.UIString("Size"); 101 101 columns.size.aligned = "right"; 102 102 columns.size.sortable = true; 103 columns.size.width = " 7%";103 columns.size.width = "6%"; 104 104 105 105 columns.http.title = WI.UIString("HTTP"); 106 106 columns.http.aligned = "centered"; 107 107 columns.http.sortable = true; 108 columns.http.width = " 7%";108 columns.http.width = "6%"; 109 109 110 110 columns.secure.title = WI.UIString("Secure"); 111 111 columns.secure.aligned = "centered"; 112 112 columns.secure.sortable = true; 113 columns.secure.width = "7%"; 113 columns.secure.width = "6%"; 114 115 columns.sameSite.title = WI.UIString("Same-Site"); 116 columns.sameSite.sortable = true; 117 columns.sameSite.width = "6%"; 114 118 115 119 this._dataGrid = new WI.DataGrid(columns, null, this._deleteCallback.bind(this)); … … 126 130 this._dataGrid.removeChildren(); 127 131 128 for ( varcookie of this._cookies) {132 for (let cookie of this._cookies) { 129 133 const checkmark = "\u2713"; 130 134 var data = { … … 137 141 http: cookie.httpOnly ? checkmark : "", 138 142 secure: cookie.secure ? checkmark : "", 143 sameSite: cookie.sameSite ? WI.Cookie.displayNameForSameSiteType(WI.Cookie.parseSameSiteAttributeValue(cookie.sameSite)) : "", 139 144 }; 140 145 … … 204 209 case "http": comparator = localeCompare.bind(this, "http"); break; 205 210 case "secure": comparator = localeCompare.bind(this, "secure"); break; 211 case "sameSite": comparator = localeCompare.bind(this, "sameSite"); break; 206 212 case "name": 207 213 default: comparator = localeCompare.bind(this, "name"); break; -
trunk/Source/WebInspectorUI/UserInterface/Views/ResourceCookiesContentView.js
r223308 r232318 90 90 cell.textContent = cookie.httpOnly ? checkmark : zeroWidthSpace; 91 91 break; 92 case "sameSite": 93 cell.textContent = cookie.sameSite === WI.Cookie.SameSiteType.None ? emDash : WI.Cookie.displayNameForSameSiteType(cookie.sameSite); 94 break; 92 95 } 93 96 … … 147 150 case "domain": 148 151 case "path": 152 case "sameSite": 149 153 // String. 150 154 comparator = (a, b) => (a[sortColumnIdentifier] || "").extendedLocaleCompare(b[sortColumnIdentifier] || ""); … … 249 253 this._responseCookiesTable.addColumn(new WI.TableColumn("secure", WI.unlocalizedString("Secure"), {minWidth: 55, maxWidth: 65, align: "center"})); 250 254 this._responseCookiesTable.addColumn(new WI.TableColumn("httpOnly", WI.unlocalizedString("HttpOnly"), {minWidth: 55, maxWidth: 65, align: "center"})); 255 this._responseCookiesTable.addColumn(new WI.TableColumn("sameSite", WI.unlocalizedString("SameSite"), {minWidth: 55, maxWidth: 65})); 251 256 if (!this._responseCookiesTable.sortColumnIdentifier) { 252 257 this._responseCookiesTable.sortOrder = WI.Table.SortOrder.Ascending;
Note: See TracChangeset
for help on using the changeset viewer.