Web Inspector: add context menu items to copy a resource's HTTP request/response...
authordrousso@apple.com <drousso@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Mon, 11 Feb 2019 22:27:37 +0000 (22:27 +0000)
committerdrousso@apple.com <drousso@apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Mon, 11 Feb 2019 22:27:37 +0000 (22:27 +0000)
https://bugs.webkit.org/show_bug.cgi?id=194261
<rdar://problem/21693696>

Reviewed by Joseph Pecoraro.

* UserInterface/Models/Resource.js:
(WI.Resource.prototype.stringifyHTTPRequest): Added.
(WI.Resource.prototype.stringifyHTTPResponse): Added.
Don't include the request/response data, as that can be very large, and can easily be
accessed by actually selecting the resource in the Resources/Network tab.

* UserInterface/Views/ContextMenuUtilities.js:
(WI.appendContextMenuItemsForSourceCode):

* Localizations/en.lproj/localizedStrings.js:

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@241279 268f45cc-cd09-0410-ab3c-d52691b4dbfc

Source/WebInspectorUI/ChangeLog
Source/WebInspectorUI/Localizations/en.lproj/localizedStrings.js
Source/WebInspectorUI/UserInterface/Models/Resource.js
Source/WebInspectorUI/UserInterface/Views/ContextMenuUtilities.js

index 35f37ac..c81b64b 100644 (file)
@@ -1,3 +1,22 @@
+2019-02-11  Devin Rousso  <drousso@apple.com>
+
+        Web Inspector: add context menu items to copy a resource's HTTP request/response data
+        https://bugs.webkit.org/show_bug.cgi?id=194261
+        <rdar://problem/21693696>
+
+        Reviewed by Joseph Pecoraro.
+
+        * UserInterface/Models/Resource.js:
+        (WI.Resource.prototype.stringifyHTTPRequest): Added.
+        (WI.Resource.prototype.stringifyHTTPResponse): Added.
+        Don't include the request/response data, as that can be very large, and can easily be
+        accessed by actually selecting the resource in the Resources/Network tab.
+
+        * UserInterface/Views/ContextMenuUtilities.js:
+        (WI.appendContextMenuItemsForSourceCode):
+
+        * Localizations/en.lproj/localizedStrings.js:
+
 2019-02-08  Devin Rousso  <drousso@apple.com>
 
         Web Inspector: Audit: show keyboard shortcut in export tooltip
index e2ab69f..b673168 100644 (file)
@@ -257,6 +257,8 @@ localizedStrings["Controls"] = "Controls";
 localizedStrings["Cookies"] = "Cookies";
 localizedStrings["Copy"] = "Copy";
 localizedStrings["Copy Action"] = "Copy Action";
+localizedStrings["Copy HTTP Request"] = "Copy HTTP Request";
+localizedStrings["Copy HTTP Response"] = "Copy HTTP Response";
 localizedStrings["Copy Link"] = "Copy Link";
 localizedStrings["Copy Path to Property"] = "Copy Path to Property";
 localizedStrings["Copy Row"] = "Copy Row";
index 66bc65b..0d87145 100644 (file)
@@ -1061,9 +1061,52 @@ WI.Resource = class Resource extends WI.SourceCode
                 command.push("--data-binary " + escapeStringPosix(this.requestData));
         }
 
-        let curlCommand = command.join(" \\\n");
-        InspectorFrontendHost.copyText(curlCommand);
-        return curlCommand;
+        return command.join(" \\\n");
+    }
+
+    stringifyHTTPRequest()
+    {
+        let lines = [];
+
+        let protocol = this.protocol || "";
+        if (protocol === "h2") {
+            // HTTP/2 Request pseudo headers:
+            // https://tools.ietf.org/html/rfc7540#section-8.1.2.3
+            lines.push(`:method: ${this.requestMethod}`);
+            lines.push(`:scheme: ${this.urlComponents.scheme}`);
+            lines.push(`:authority: ${WI.h2Authority(this.urlComponents)}`);
+            lines.push(`:path: ${WI.h2Path(this.urlComponents)}`);
+        } else {
+            // HTTP/1.1 request line:
+            // https://www.w3.org/Protocols/rfc2616/rfc2616-sec5.html#sec5.1
+            lines.push(`${this.requestMethod} ${this.urlComponents.path}${protocol ? " " + protocol.toUpperCase() : ""}`);
+        }
+
+        for (let key in this.requestHeaders)
+            lines.push(`${key}: ${this.requestHeaders[key]}`);
+
+        return lines.join("\n") + "\n";
+    }
+
+    stringifyHTTPResponse()
+    {
+        let lines = [];
+
+        let protocol = this.protocol || "";
+        if (protocol === "h2") {
+            // HTTP/2 Response pseudo headers:
+            // https://tools.ietf.org/html/rfc7540#section-8.1.2.4
+            lines.push(`:status: ${this.statusCode}`);
+        } else {
+            // HTTP/1.1 response status line:
+            // https://www.w3.org/Protocols/rfc2616/rfc2616-sec6.html#sec6.1
+            lines.push(`${protocol ? protocol.toUpperCase() + " " : ""}${this.statusCode} ${this.statusText}`);
+        }
+
+        for (let key in this.responseHeaders)
+            lines.push(`${key}: ${this.responseHeaders[key]}`);
+
+        return lines.join("\n") + "\n";
     }
 
     async showCertificate()
index b543529..9123d0c 100644 (file)
@@ -47,8 +47,22 @@ WI.appendContextMenuItemsForSourceCode = function(contextMenu, sourceCodeOrLocat
     if (sourceCode instanceof WI.Resource) {
         if (sourceCode.urlComponents.scheme !== "data") {
             contextMenu.appendItem(WI.UIString("Copy as cURL"), () => {
-                sourceCode.generateCURLCommand();
+                InspectorFrontendHost.copyText(sourceCode.generateCURLCommand());
             });
+
+            contextMenu.appendSeparator();
+
+            contextMenu.appendItem(WI.UIString("Copy HTTP Request"), () => {
+                InspectorFrontendHost.copyText(sourceCode.stringifyHTTPRequest());
+            });
+
+            if (sourceCode.hasResponse()) {
+                contextMenu.appendItem(WI.UIString("Copy HTTP Response"), () => {
+                    InspectorFrontendHost.copyText(sourceCode.stringifyHTTPResponse());
+                });
+            }
+
+            contextMenu.appendSeparator();
         }
     }