OLD | NEW |
---|---|
(Empty) | |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | |
2 // Use of this source code is governed by a BSD-style license that can be | |
3 // found in the LICENSE file. | |
4 | |
5 #include "config.h" | |
6 #include "modules/beacon/NavigatorBeacon.h" | |
7 | |
8 #include "bindings/v8/ExceptionState.h" | |
9 #include "core/dom/ExceptionCode.h" | |
10 #include "core/dom/ExecutionContext.h" | |
11 #include "core/fileapi/Blob.h" | |
12 #include "core/frame/LocalFrame.h" | |
13 #include "core/frame/Settings.h" | |
14 #include "core/frame/csp/ContentSecurityPolicy.h" | |
15 #include "core/html/DOMFormData.h" | |
16 #include "core/loader/BeaconLoader.h" | |
17 #include "wtf/ArrayBufferView.h" | |
18 | |
19 namespace WebCore { | |
20 | |
21 NavigatorBeacon::NavigatorBeacon(Navigator& navigator) | |
22 : m_transmittedBytes(0) | |
23 , m_navigator(navigator) | |
24 { | |
25 } | |
26 | |
27 const char* NavigatorBeacon::supplementName() | |
28 { | |
29 return "NavigatorBeacon"; | |
30 } | |
31 | |
32 NavigatorBeacon& NavigatorBeacon::from(Navigator& navigator) | |
33 { | |
34 NavigatorBeacon* supplement = static_cast<NavigatorBeacon*>(WillBeHeapSupple ment<Navigator>::from(navigator, supplementName())); | |
35 if (!supplement) { | |
36 supplement = new NavigatorBeacon(navigator); | |
37 provideTo(navigator, supplementName(), adoptPtrWillBeNoop(supplement)); | |
38 } | |
39 return *supplement; | |
40 } | |
41 | |
42 bool NavigatorBeacon::isAllowedAccess(ExecutionContext* context, const KURL& url , ExceptionState& exceptionState) | |
abarth-chromium
2014/05/08 13:15:25
s/isAllowedAccess/canSendBeacon/ ?
sof
2014/05/08 20:47:07
That captures purpose more precisely, I like it. A
| |
43 { | |
44 if (!url.isValid()) { | |
45 exceptionState.throwDOMException(SyntaxError, "The URL argument is ill-f ormed or unsupported."); | |
46 return false; | |
47 } | |
48 // For now, only support HTTP and related. | |
49 if (!url.protocolIsInHTTPFamily()) { | |
50 exceptionState.throwDOMException(SyntaxError, "Beacons are only supporte d over HTTP(S)."); | |
51 return false; | |
52 } | |
53 if (!ContentSecurityPolicy::shouldBypassMainWorld(context) && !context->cont entSecurityPolicy()->allowConnectToSource(url)) { | |
54 // We can safely expose the URL to JavaScript, as these checks happen sy nchronously before redirection. JavaScript receives no new information. | |
55 exceptionState.throwSecurityError("Refused to send beacon to '" + url.el idedString() + "' because it violates the document's Content Security Policy."); | |
56 return false; | |
57 } | |
58 | |
59 // Do not allow sending Beacons over a Navigator that is detached. | |
60 if (!m_navigator.frame()) | |
61 return false; | |
62 | |
63 return true; | |
64 } | |
65 | |
66 int NavigatorBeacon::maxAllowance() const | |
67 { | |
68 const Settings* settings = m_navigator.frame() ? m_navigator.frame()->settin gs() : 0; | |
69 if (settings) { | |
abarth-chromium
2014/05/08 13:15:25
We usually combine these lines.
I don't think we
sof
2014/05/08 20:47:07
Yes, removed the null check.
| |
70 int maxAllowed = settings->maxBeaconTransmission(); | |
71 if (maxAllowed < m_transmittedBytes) | |
72 return 0; | |
73 return maxAllowed - m_transmittedBytes; | |
74 } | |
75 return m_transmittedBytes; | |
76 } | |
77 | |
78 void NavigatorBeacon::updateTransmittedBytes(int length) | |
79 { | |
80 ASSERT(length >= 0); | |
81 m_transmittedBytes += length; | |
82 } | |
83 | |
84 bool NavigatorBeacon::sendBeacon(ExecutionContext* context, Navigator& navigator , const String& urlstring, const String& data, ExceptionState& exceptionState) | |
85 { | |
86 return NavigatorBeacon::from(navigator).sendBeacon(context, urlstring, data, exceptionState); | |
87 } | |
88 | |
89 bool NavigatorBeacon::sendBeacon(ExecutionContext* context, const String& urlstr ing, const String& data, ExceptionState& exceptionState) | |
90 { | |
91 KURL url = context->completeURL(urlstring); | |
92 if (!isAllowedAccess(context, url, exceptionState)) | |
93 return false; | |
94 | |
95 int bytes = 0; | |
96 bool result = BeaconLoader::sendBeacon(m_navigator.frame(), maxAllowance(), url, data, bytes); | |
97 if (result) | |
98 updateTransmittedBytes(bytes); | |
99 | |
100 return result; | |
101 } | |
102 | |
103 bool NavigatorBeacon::sendBeacon(ExecutionContext* context, Navigator& navigator , const String& urlstring, PassRefPtr<ArrayBufferView> data, ExceptionState& exc eptionState) | |
104 { | |
105 return NavigatorBeacon::from(navigator).sendBeacon(context, urlstring, data, exceptionState); | |
106 } | |
107 | |
108 bool NavigatorBeacon::sendBeacon(ExecutionContext* context, const String& urlstr ing, PassRefPtr<ArrayBufferView> data, ExceptionState& exceptionState) | |
109 { | |
110 KURL url = context->completeURL(urlstring); | |
111 if (!isAllowedAccess(context, url, exceptionState)) | |
112 return false; | |
113 | |
114 int bytes = 0; | |
115 bool result = BeaconLoader::sendBeacon(m_navigator.frame(), maxAllowance(), url, data, bytes); | |
116 if (result) | |
117 updateTransmittedBytes(bytes); | |
118 | |
119 return result; | |
120 } | |
121 | |
122 bool NavigatorBeacon::sendBeacon(ExecutionContext* context, Navigator& navigator , const String& urlstring, PassRefPtrWillBeRawPtr<Blob> data, ExceptionState& ex ceptionState) | |
123 { | |
124 return NavigatorBeacon::from(navigator).sendBeacon(context, urlstring, data, exceptionState); | |
125 } | |
126 | |
127 bool NavigatorBeacon::sendBeacon(ExecutionContext* context, const String& urlstr ing, PassRefPtrWillBeRawPtr<Blob> data, ExceptionState& exceptionState) | |
128 { | |
129 KURL url = context->completeURL(urlstring); | |
130 if (!isAllowedAccess(context, url, exceptionState)) | |
131 return false; | |
132 | |
133 int bytes = 0; | |
134 bool result = BeaconLoader::sendBeacon(m_navigator.frame(), maxAllowance(), url, data, bytes); | |
135 if (result) | |
136 updateTransmittedBytes(bytes); | |
137 | |
138 return result; | |
139 } | |
140 | |
141 bool NavigatorBeacon::sendBeacon(ExecutionContext* context, Navigator& navigator , const String& urlstring, PassRefPtrWillBeRawPtr<DOMFormData> data, ExceptionSt ate& exceptionState) | |
142 { | |
143 return NavigatorBeacon::from(navigator).sendBeacon(context, urlstring, data, exceptionState); | |
144 } | |
145 | |
146 bool NavigatorBeacon::sendBeacon(ExecutionContext* context, const String& urlstr ing, PassRefPtrWillBeRawPtr<DOMFormData> data, ExceptionState& exceptionState) | |
147 { | |
148 KURL url = context->completeURL(urlstring); | |
149 if (!isAllowedAccess(context, url, exceptionState)) | |
150 return false; | |
151 | |
152 int bytes = 0; | |
153 bool result = BeaconLoader::sendBeacon(m_navigator.frame(), maxAllowance(), url, data, bytes); | |
154 if (result) | |
155 updateTransmittedBytes(bytes); | |
156 | |
157 return result; | |
158 } | |
159 | |
160 } // namespace WebCore | |
OLD | NEW |