OLD | NEW |
(Empty) | |
| 1 /* |
| 2 * Copyright (C) 2007, 2008 Apple Inc. All rights reserved. |
| 3 * Copyright (C) IBM Corp. 2009 All rights reserved. |
| 4 * |
| 5 * Redistribution and use in source and binary forms, with or without |
| 6 * modification, are permitted provided that the following conditions |
| 7 * are met: |
| 8 * |
| 9 * 1. Redistributions of source code must retain the above copyright |
| 10 * notice, this list of conditions and the following disclaimer. |
| 11 * 2. Redistributions in binary form must reproduce the above copyright |
| 12 * notice, this list of conditions and the following disclaimer in the |
| 13 * documentation and/or other materials provided with the distribution. |
| 14 * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of |
| 15 * its contributors may be used to endorse or promote products derived |
| 16 * from this software without specific prior written permission. |
| 17 * |
| 18 * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY |
| 19 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
| 20 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |
| 21 * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY |
| 22 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |
| 23 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |
| 24 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |
| 25 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
| 26 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF |
| 27 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
| 28 */ |
| 29 |
| 30 WebInspector.ResourceView = function(resource) |
| 31 { |
| 32 WebInspector.View.call(this); |
| 33 |
| 34 this.element.addStyleClass("resource-view"); |
| 35 |
| 36 this.resource = resource; |
| 37 |
| 38 this.headersElement = document.createElement("div"); |
| 39 this.headersElement.className = "resource-view-headers"; |
| 40 this.element.appendChild(this.headersElement); |
| 41 |
| 42 this.contentElement = document.createElement("div"); |
| 43 this.contentElement.className = "resource-view-content"; |
| 44 this.element.appendChild(this.contentElement); |
| 45 |
| 46 this.headersListElement = document.createElement("ol"); |
| 47 this.headersListElement.className = "outline-disclosure"; |
| 48 this.headersElement.appendChild(this.headersListElement); |
| 49 |
| 50 this.headersTreeOutline = new TreeOutline(this.headersListElement); |
| 51 this.headersTreeOutline.expandTreeElementsWhenArrowing = true; |
| 52 |
| 53 this.urlTreeElement = new TreeElement("", null, false); |
| 54 this.urlTreeElement.selectable = false; |
| 55 this.headersTreeOutline.appendChild(this.urlTreeElement); |
| 56 |
| 57 this.requestHeadersTreeElement = new TreeElement("", null, true); |
| 58 this.requestHeadersTreeElement.expanded = false; |
| 59 this.requestHeadersTreeElement.selectable = false; |
| 60 this.headersTreeOutline.appendChild(this.requestHeadersTreeElement); |
| 61 |
| 62 this._decodeHover = WebInspector.UIString("Double-Click to toggle between UR
L encoded and decoded formats"); |
| 63 this._decodeRequestParameters = true; |
| 64 |
| 65 this.queryStringTreeElement = new TreeElement("", null, true); |
| 66 this.queryStringTreeElement.expanded = false; |
| 67 this.queryStringTreeElement.selectable = false; |
| 68 this.queryStringTreeElement.hidden = true; |
| 69 this.headersTreeOutline.appendChild(this.queryStringTreeElement); |
| 70 |
| 71 this.formDataTreeElement = new TreeElement("", null, true); |
| 72 this.formDataTreeElement.expanded = false; |
| 73 this.formDataTreeElement.selectable = false; |
| 74 this.formDataTreeElement.hidden = true; |
| 75 this.headersTreeOutline.appendChild(this.formDataTreeElement); |
| 76 |
| 77 this.requestPayloadTreeElement = new TreeElement(WebInspector.UIString("Requ
est Payload"), null, true); |
| 78 this.requestPayloadTreeElement.expanded = false; |
| 79 this.requestPayloadTreeElement.selectable = false; |
| 80 this.requestPayloadTreeElement.hidden = true; |
| 81 this.headersTreeOutline.appendChild(this.requestPayloadTreeElement); |
| 82 |
| 83 this.responseHeadersTreeElement = new TreeElement("", null, true); |
| 84 this.responseHeadersTreeElement.expanded = false; |
| 85 this.responseHeadersTreeElement.selectable = false; |
| 86 this.headersTreeOutline.appendChild(this.responseHeadersTreeElement); |
| 87 |
| 88 this.headersVisible = true; |
| 89 |
| 90 resource.addEventListener("url changed", this._refreshURL, this); |
| 91 resource.addEventListener("requestHeaders changed", this._refreshRequestHead
ers, this); |
| 92 resource.addEventListener("responseHeaders changed", this._refreshResponseHe
aders, this); |
| 93 |
| 94 this._refreshURL(); |
| 95 this._refreshRequestHeaders(); |
| 96 this._refreshResponseHeaders(); |
| 97 } |
| 98 |
| 99 WebInspector.ResourceView.prototype = { |
| 100 get headersVisible() |
| 101 { |
| 102 return this._headersVisible; |
| 103 }, |
| 104 |
| 105 set headersVisible(x) |
| 106 { |
| 107 if (x === this._headersVisible) |
| 108 return; |
| 109 |
| 110 this._headersVisible = x; |
| 111 |
| 112 if (x) |
| 113 this.element.addStyleClass("headers-visible"); |
| 114 else |
| 115 this.element.removeStyleClass("headers-visible"); |
| 116 }, |
| 117 |
| 118 attach: function() |
| 119 { |
| 120 if (!this.element.parentNode) { |
| 121 var parentElement = (document.getElementById("resource-views") || do
cument.getElementById("script-resource-views")); |
| 122 if (parentElement) |
| 123 parentElement.appendChild(this.element); |
| 124 } |
| 125 }, |
| 126 |
| 127 _refreshURL: function() |
| 128 { |
| 129 var url = this.resource.url; |
| 130 this.urlTreeElement.title = this.resource.requestMethod + " " + url.esca
peHTML(); |
| 131 this._refreshQueryString(); |
| 132 }, |
| 133 |
| 134 _refreshQueryString: function() |
| 135 { |
| 136 var url = this.resource.url; |
| 137 var hasQueryString = url.indexOf("?") >= 0; |
| 138 |
| 139 if (!hasQueryString) { |
| 140 this.queryStringTreeElement.hidden = true; |
| 141 return; |
| 142 } |
| 143 |
| 144 this.queryStringTreeElement.hidden = false; |
| 145 var parmString = url.split("?", 2)[1]; |
| 146 this._refreshParms(WebInspector.UIString("Query String Parameters"), par
mString, this.queryStringTreeElement); |
| 147 }, |
| 148 |
| 149 _refreshFormData: function() |
| 150 { |
| 151 this.formDataTreeElement.hidden = true; |
| 152 this.requestPayloadTreeElement.hidden = true; |
| 153 |
| 154 var isFormData = this.resource.requestFormData; |
| 155 if (!isFormData) |
| 156 return; |
| 157 |
| 158 var isFormEncoded = false; |
| 159 var requestContentType = this._getHeaderValue(this.resource.requestHeade
rs, "Content-Type"); |
| 160 if (requestContentType == "application/x-www-form-urlencoded") |
| 161 isFormEncoded = true; |
| 162 |
| 163 if (isFormEncoded) { |
| 164 this.formDataTreeElement.hidden = false; |
| 165 this._refreshParms(WebInspector.UIString("Form Data"), this.resource
.requestFormData, this.formDataTreeElement); |
| 166 } else { |
| 167 this.requestPayloadTreeElement.hidden = false; |
| 168 this._refreshRequestPayload(this.resource.requestFormData); |
| 169 } |
| 170 }, |
| 171 |
| 172 _refreshRequestPayload: function(formData) |
| 173 { |
| 174 this.requestPayloadTreeElement.removeChildren(); |
| 175 |
| 176 var title = "<div class=\"header-name\"> </div>"; |
| 177 title += "<div class=\"raw-form-data header-value\">" + formData.escapeH
TML() + "</div>"; |
| 178 var parmTreeElement = new TreeElement(title, null, false); |
| 179 this.requestPayloadTreeElement.appendChild(parmTreeElement); |
| 180 }, |
| 181 |
| 182 _refreshParms: function(title, parmString, parmsTreeElement) |
| 183 { |
| 184 var parms = parmString.split("&"); |
| 185 for (var i = 0; i < parms.length; ++i) { |
| 186 var parm = parms[i]; |
| 187 parm = parm.split("=", 2); |
| 188 if (parm.length == 1) |
| 189 parm.push(""); |
| 190 parms[i] = parm; |
| 191 } |
| 192 |
| 193 parmsTreeElement.removeChildren(); |
| 194 |
| 195 parmsTreeElement.title = title + "<span class=\"header-count\">" + WebIn
spector.UIString(" (%d)", parms.length) + "</span>"; |
| 196 |
| 197 for (var i = 0; i < parms.length; ++i) { |
| 198 var key = parms[i][0]; |
| 199 var val = parms[i][1]; |
| 200 |
| 201 if (val.indexOf("%") >= 0) |
| 202 if (this._decodeRequestParameters) |
| 203 val = decodeURIComponent(val).replace(/\+/g, " "); |
| 204 |
| 205 var title = "<div class=\"header-name\">" + key.escapeHTML() + ":</d
iv>"; |
| 206 title += "<div class=\"header-value\">" + val.escapeHTML() + "</div>
"; |
| 207 |
| 208 var parmTreeElement = new TreeElement(title, null, false); |
| 209 parmTreeElement.selectable = false; |
| 210 parmTreeElement.tooltip = this._decodeHover; |
| 211 parmTreeElement.ondblclick = this._toggleURLdecoding.bind(this); |
| 212 parmsTreeElement.appendChild(parmTreeElement); |
| 213 } |
| 214 }, |
| 215 |
| 216 _toggleURLdecoding: function(treeElement, event) |
| 217 { |
| 218 this._decodeRequestParameters = !this._decodeRequestParameters; |
| 219 this._refreshQueryString(); |
| 220 this._refreshFormData(); |
| 221 }, |
| 222 |
| 223 _getHeaderValue: function(headers, key) |
| 224 { |
| 225 var lowerKey = key.toLowerCase(); |
| 226 for (var testKey in headers) { |
| 227 if (testKey.toLowerCase() === lowerKey) |
| 228 return headers[testKey]; |
| 229 } |
| 230 }, |
| 231 |
| 232 _refreshRequestHeaders: function() |
| 233 { |
| 234 this._refreshHeaders(WebInspector.UIString("Request Headers"), this.reso
urce.sortedRequestHeaders, this.requestHeadersTreeElement); |
| 235 this._refreshFormData(); |
| 236 }, |
| 237 |
| 238 _refreshResponseHeaders: function() |
| 239 { |
| 240 this._refreshHeaders(WebInspector.UIString("Response Headers"), this.res
ource.sortedResponseHeaders, this.responseHeadersTreeElement); |
| 241 }, |
| 242 |
| 243 _refreshHeaders: function(title, headers, headersTreeElement) |
| 244 { |
| 245 headersTreeElement.removeChildren(); |
| 246 |
| 247 var length = headers.length; |
| 248 headersTreeElement.title = title.escapeHTML() + "<span class=\"header-co
unt\">" + WebInspector.UIString(" (%d)", length) + "</span>"; |
| 249 headersTreeElement.hidden = !length; |
| 250 |
| 251 var length = headers.length; |
| 252 for (var i = 0; i < length; ++i) { |
| 253 var title = "<div class=\"header-name\">" + headers[i].header.escape
HTML() + ":</div>"; |
| 254 title += "<div class=\"header-value\">" + headers[i].value.escapeHTM
L() + "</div>" |
| 255 |
| 256 var headerTreeElement = new TreeElement(title, null, false); |
| 257 headerTreeElement.selectable = false; |
| 258 headersTreeElement.appendChild(headerTreeElement); |
| 259 } |
| 260 } |
| 261 } |
| 262 |
| 263 WebInspector.ResourceView.prototype.__proto__ = WebInspector.View.prototype; |
OLD | NEW |