| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "modules/permissions/Permissions.h" | 5 #include "modules/permissions/Permissions.h" |
| 6 | 6 |
| 7 #include "bindings/core/v8/Dictionary.h" | 7 #include "bindings/core/v8/Dictionary.h" |
| 8 #include "bindings/core/v8/Nullable.h" | 8 #include "bindings/core/v8/Nullable.h" |
| 9 #include "bindings/core/v8/ScriptPromise.h" | 9 #include "bindings/core/v8/ScriptPromise.h" |
| 10 #include "bindings/core/v8/ScriptPromiseResolver.h" | 10 #include "bindings/core/v8/ScriptPromiseResolver.h" |
| 11 #include "bindings/modules/v8/V8MidiPermissionDescriptor.h" | 11 #include "bindings/modules/v8/V8MidiPermissionDescriptor.h" |
| 12 #include "bindings/modules/v8/V8PermissionDescriptor.h" | 12 #include "bindings/modules/v8/V8PermissionDescriptor.h" |
| 13 #include "bindings/modules/v8/V8PushPermissionDescriptor.h" | 13 #include "bindings/modules/v8/V8PushPermissionDescriptor.h" |
| 14 #include "core/dom/DOMException.h" | 14 #include "core/dom/DOMException.h" |
| 15 #include "core/dom/Document.h" | 15 #include "core/dom/Document.h" |
| 16 #include "core/dom/ExceptionCode.h" | 16 #include "core/dom/ExceptionCode.h" |
| 17 #include "modules/permissions/PermissionCallback.h" | 17 #include "core/frame/LocalFrame.h" |
| 18 #include "modules/permissions/PermissionController.h" | |
| 19 #include "modules/permissions/PermissionDescriptor.h" | 18 #include "modules/permissions/PermissionDescriptor.h" |
| 20 #include "modules/permissions/PermissionStatus.h" | 19 #include "modules/permissions/PermissionStatus.h" |
| 21 #include "modules/permissions/PermissionsCallback.h" | |
| 22 #include "platform/Logging.h" | 20 #include "platform/Logging.h" |
| 21 #include "platform/UserGestureIndicator.h" |
| 23 #include "public/platform/Platform.h" | 22 #include "public/platform/Platform.h" |
| 24 #include "public/platform/modules/permissions/WebPermissionClient.h" | 23 #include "public/platform/ServiceRegistry.h" |
| 24 #include "wtf/Functional.h" |
| 25 #include "wtf/NotFound.h" | 25 #include "wtf/NotFound.h" |
| 26 #include "wtf/PtrUtil.h" | 26 #include "wtf/PtrUtil.h" |
| 27 #include "wtf/Vector.h" | 27 #include "wtf/Vector.h" |
| 28 #include <memory> | 28 #include <memory> |
| 29 | 29 |
| 30 namespace blink { | 30 namespace blink { |
| 31 | 31 |
| 32 using mojom::blink::PermissionName; |
| 33 using mojom::blink::PermissionService; |
| 34 |
| 32 namespace { | 35 namespace { |
| 33 | 36 |
| 34 // Websites will be able to run code when `name()` is called, changing the | 37 // Websites will be able to run code when `name()` is called, changing the |
| 35 // current context. The caller should make sure that no assumption is made | 38 // current context. The caller should make sure that no assumption is made |
| 36 // after this has been called. | 39 // after this has been called. |
| 37 WebPermissionType getPermissionType(ScriptState* scriptState, const Dictionary&
rawPermission, const PermissionDescriptor& permission, ExceptionState& exception
State) | 40 PermissionName getPermissionName(ScriptState* scriptState, const Dictionary& raw
Permission, const PermissionDescriptor& permission, ExceptionState& exceptionSta
te) |
| 38 { | 41 { |
| 39 const String& name = permission.name(); | 42 const String& name = permission.name(); |
| 40 if (name == "geolocation") | 43 if (name == "geolocation") |
| 41 return WebPermissionTypeGeolocation; | 44 return PermissionName::GEOLOCATION; |
| 42 if (name == "notifications") | 45 if (name == "notifications") |
| 43 return WebPermissionTypeNotifications; | 46 return PermissionName::NOTIFICATIONS; |
| 44 if (name == "push") | 47 if (name == "push") |
| 45 return WebPermissionTypePushNotifications; | 48 return PermissionName::PUSH_NOTIFICATIONS; |
| 46 if (name == "midi") { | 49 if (name == "midi") { |
| 47 MidiPermissionDescriptor midiPermission = NativeValueTraits<MidiPermissi
onDescriptor>::nativeValue(scriptState->isolate(), rawPermission.v8Value(), exce
ptionState); | 50 MidiPermissionDescriptor midiPermission = NativeValueTraits<MidiPermissi
onDescriptor>::nativeValue(scriptState->isolate(), rawPermission.v8Value(), exce
ptionState); |
| 48 return midiPermission.sysex() ? WebPermissionTypeMidiSysEx : WebPermissi
onTypeMidi; | 51 return midiPermission.sysex() ? PermissionName::MIDI_SYSEX : PermissionN
ame::MIDI; |
| 49 } | 52 } |
| 50 if (name == "background-sync") | 53 if (name == "background-sync") |
| 51 return WebPermissionTypeBackgroundSync; | 54 return PermissionName::BACKGROUND_SYNC; |
| 52 | 55 |
| 53 ASSERT_NOT_REACHED(); | 56 ASSERT_NOT_REACHED(); |
| 54 return WebPermissionTypeGeolocation; | 57 return PermissionName::GEOLOCATION; |
| 55 } | 58 } |
| 56 | 59 |
| 57 // Parses the raw permission dictionary and returns the PermissionType if | 60 // Parses the raw permission dictionary and returns the PermissionType if |
| 58 // parsing was successful. If an exception occurs, it will be stored in | 61 // parsing was successful. If an exception occurs, it will be stored in |
| 59 // |exceptionState| and null will be returned. Therefore, the |exceptionState| | 62 // |exceptionState| and null will be returned. Therefore, the |exceptionState| |
| 60 // should be checked before attempting to use the returned permission as the | 63 // should be checked before attempting to use the returned permission as the |
| 61 // non-null assert will be fired otherwise. | 64 // non-null assert will be fired otherwise. |
| 62 Nullable<WebPermissionType> parsePermission(ScriptState* scriptState, const Dict
ionary rawPermission, ExceptionState& exceptionState) | 65 Nullable<PermissionName> parsePermission(ScriptState* scriptState, const Diction
ary rawPermission, ExceptionState& exceptionState) |
| 63 { | 66 { |
| 64 PermissionDescriptor permission = NativeValueTraits<PermissionDescriptor>::n
ativeValue(scriptState->isolate(), rawPermission.v8Value(), exceptionState); | 67 PermissionDescriptor permission = NativeValueTraits<PermissionDescriptor>::n
ativeValue(scriptState->isolate(), rawPermission.v8Value(), exceptionState); |
| 65 | 68 |
| 66 if (exceptionState.hadException()) { | 69 if (exceptionState.hadException()) { |
| 67 exceptionState.throwTypeError(exceptionState.message()); | 70 exceptionState.throwTypeError(exceptionState.message()); |
| 68 return Nullable<WebPermissionType>(); | 71 return Nullable<PermissionName>(); |
| 69 } | 72 } |
| 70 | 73 |
| 71 WebPermissionType type = getPermissionType(scriptState, rawPermission, permi
ssion, exceptionState); | 74 PermissionName name = getPermissionName(scriptState, rawPermission, permissi
on, exceptionState); |
| 72 if (exceptionState.hadException()) { | 75 if (exceptionState.hadException()) { |
| 73 exceptionState.throwTypeError(exceptionState.message()); | 76 exceptionState.throwTypeError(exceptionState.message()); |
| 74 return Nullable<WebPermissionType>(); | 77 return Nullable<PermissionName>(); |
| 75 } | 78 } |
| 76 | 79 |
| 77 // Here we reject any permissions which are not yet supported by Blink. | 80 // Here we reject any permissions which are not yet supported by Blink. |
| 78 if (type == WebPermissionTypePushNotifications) { | 81 if (name == PermissionName::PUSH_NOTIFICATIONS) { |
| 79 PushPermissionDescriptor pushPermission = NativeValueTraits<PushPermissi
onDescriptor>::nativeValue(scriptState->isolate(), rawPermission.v8Value(), exce
ptionState); | 82 PushPermissionDescriptor pushPermission = NativeValueTraits<PushPermissi
onDescriptor>::nativeValue(scriptState->isolate(), rawPermission.v8Value(), exce
ptionState); |
| 80 if (exceptionState.hadException()) { | 83 if (exceptionState.hadException()) { |
| 81 exceptionState.throwTypeError(exceptionState.message()); | 84 exceptionState.throwTypeError(exceptionState.message()); |
| 82 return Nullable<WebPermissionType>(); | 85 return Nullable<PermissionName>(); |
| 83 } | 86 } |
| 84 | 87 |
| 85 // Only "userVisibleOnly" push is supported for now. | 88 // Only "userVisibleOnly" push is supported for now. |
| 86 if (!pushPermission.userVisibleOnly()) { | 89 if (!pushPermission.userVisibleOnly()) { |
| 87 exceptionState.throwDOMException(NotSupportedError, "Push Permission
without userVisibleOnly:true isn't supported yet."); | 90 exceptionState.throwDOMException(NotSupportedError, "Push Permission
without userVisibleOnly:true isn't supported yet."); |
| 88 return Nullable<WebPermissionType>(); | 91 return Nullable<PermissionName>(); |
| 89 } | 92 } |
| 90 } | 93 } |
| 91 | 94 |
| 92 return Nullable<WebPermissionType>(type); | 95 return Nullable<PermissionName>(name); |
| 93 } | 96 } |
| 94 | 97 |
| 95 } // anonymous namespace | 98 } // anonymous namespace |
| 96 | 99 |
| 97 // static | 100 // static |
| 98 WebPermissionClient* Permissions::getClient(ExecutionContext* executionContext) | 101 bool Permissions::connectToService(ExecutionContext* executionContext, mojom::bl
ink::PermissionServiceRequest request) |
| 99 { | 102 { |
| 103 ServiceRegistry* serviceRegistry = nullptr; |
| 100 if (executionContext->isDocument()) { | 104 if (executionContext->isDocument()) { |
| 101 Document* document = toDocument(executionContext); | 105 Document* document = toDocument(executionContext); |
| 102 if (!document->frame()) | 106 if (document->frame()) |
| 103 return nullptr; | 107 serviceRegistry = document->frame()->serviceRegistry(); |
| 104 PermissionController* controller = PermissionController::from(*document-
>frame()); | 108 } else { |
| 105 return controller ? controller->client() : nullptr; | 109 serviceRegistry = Platform::current()->serviceRegistry(); |
| 106 } | 110 } |
| 107 return Platform::current()->permissionClient(); | 111 |
| 112 if (serviceRegistry) |
| 113 serviceRegistry->connectToRemoteService(std::move(request)); |
| 114 return serviceRegistry; |
| 108 } | 115 } |
| 109 | 116 |
| 110 ScriptPromise Permissions::query(ScriptState* scriptState, const Dictionary& raw
Permission) | 117 ScriptPromise Permissions::query(ScriptState* scriptState, const Dictionary& raw
Permission) |
| 111 { | 118 { |
| 112 ExceptionState exceptionState(ExceptionState::GetterContext, "query", "Perm
issions", scriptState->context()->Global(), scriptState->isolate()); | 119 ExceptionState exceptionState(ExceptionState::GetterContext, "query", "Perm
issions", scriptState->context()->Global(), scriptState->isolate()); |
| 113 Nullable<WebPermissionType> type = parsePermission(scriptState, rawPermissio
n, exceptionState); | 120 Nullable<PermissionName> name = parsePermission(scriptState, rawPermission,
exceptionState); |
| 114 if (exceptionState.hadException()) | 121 if (exceptionState.hadException()) |
| 115 return exceptionState.reject(scriptState); | 122 return exceptionState.reject(scriptState); |
| 116 | 123 |
| 117 // This must be called after `parsePermission` because the website might | 124 // This must be called after `parsePermission` because the website might |
| 118 // be able to run code. | 125 // be able to run code. |
| 119 WebPermissionClient* client = getClient(scriptState->getExecutionContext()); | 126 PermissionService* service = getService(scriptState->getExecutionContext()); |
| 120 if (!client) | 127 if (!service) |
| 121 return ScriptPromise::rejectWithDOMException(scriptState, DOMException::
create(InvalidStateError, "In its current state, the global scope can't query pe
rmissions.")); | 128 return ScriptPromise::rejectWithDOMException(scriptState, DOMException::
create(InvalidStateError, "In its current state, the global scope can't query pe
rmissions.")); |
| 122 | 129 |
| 123 ScriptPromiseResolver* resolver = ScriptPromiseResolver::create(scriptState)
; | 130 ScriptPromiseResolver* resolver = ScriptPromiseResolver::create(scriptState)
; |
| 124 ScriptPromise promise = resolver->promise(); | 131 ScriptPromise promise = resolver->promise(); |
| 125 | 132 |
| 126 // If the current origin is a file scheme, it will unlikely return a | 133 // If the current origin is a file scheme, it will unlikely return a |
| 127 // meaningful value because most APIs are broken on file scheme and no | 134 // meaningful value because most APIs are broken on file scheme and no |
| 128 // permission prompt will be shown even if the returned permission will most | 135 // permission prompt will be shown even if the returned permission will most |
| 129 // likely be "prompt". | 136 // likely be "prompt". |
| 130 client->queryPermission(type.get(), KURL(KURL(), scriptState->getExecutionCo
ntext()->getSecurityOrigin()->toString()), new PermissionCallback(resolver, type
.get())); | 137 service->HasPermission(name.get(), scriptState->getExecutionContext()->getSe
curityOrigin()->toString(), convertToBaseCallback(WTF::bind(&Permissions::taskCo
mplete, wrapPersistent(this), wrapPersistent(resolver), name.get()))); |
| 131 return promise; | 138 return promise; |
| 132 } | 139 } |
| 133 | 140 |
| 134 ScriptPromise Permissions::request(ScriptState* scriptState, const Dictionary& r
awPermission) | 141 ScriptPromise Permissions::request(ScriptState* scriptState, const Dictionary& r
awPermission) |
| 135 { | 142 { |
| 136 ExceptionState exceptionState(ExceptionState::GetterContext, "request", "Pe
rmissions", scriptState->context()->Global(), scriptState->isolate()); | 143 ExceptionState exceptionState(ExceptionState::GetterContext, "request", "Pe
rmissions", scriptState->context()->Global(), scriptState->isolate()); |
| 137 Nullable<WebPermissionType> type = parsePermission(scriptState, rawPermissio
n, exceptionState); | 144 Nullable<PermissionName> name = parsePermission(scriptState, rawPermission,
exceptionState); |
| 138 if (exceptionState.hadException()) | 145 if (exceptionState.hadException()) |
| 139 return exceptionState.reject(scriptState); | 146 return exceptionState.reject(scriptState); |
| 140 | 147 |
| 141 // This must be called after `parsePermission` because the website might | 148 // This must be called after `parsePermission` because the website might |
| 142 // be able to run code. | 149 // be able to run code. |
| 143 WebPermissionClient* client = getClient(scriptState->getExecutionContext()); | 150 PermissionService* service = getService(scriptState->getExecutionContext()); |
| 144 if (!client) | 151 if (!service) |
| 145 return ScriptPromise::rejectWithDOMException(scriptState, DOMException::
create(InvalidStateError, "In its current state, the global scope can't request
permissions.")); | 152 return ScriptPromise::rejectWithDOMException(scriptState, DOMException::
create(InvalidStateError, "In its current state, the global scope can't request
permissions.")); |
| 146 | 153 |
| 147 ScriptPromiseResolver* resolver = ScriptPromiseResolver::create(scriptState)
; | 154 ScriptPromiseResolver* resolver = ScriptPromiseResolver::create(scriptState)
; |
| 148 ScriptPromise promise = resolver->promise(); | 155 ScriptPromise promise = resolver->promise(); |
| 149 | 156 |
| 150 client->requestPermission(type.get(), KURL(KURL(), scriptState->getExecution
Context()->getSecurityOrigin()->toString()), new PermissionCallback(resolver, ty
pe.get())); | 157 service->RequestPermission(name.get(), scriptState->getExecutionContext()->g
etSecurityOrigin()->toString(), UserGestureIndicator::processingUserGesture(), c
onvertToBaseCallback(WTF::bind(&Permissions::taskComplete, wrapPersistent(this),
wrapPersistent(resolver), name.get()))); |
| 151 return promise; | 158 return promise; |
| 152 } | 159 } |
| 153 | 160 |
| 154 ScriptPromise Permissions::revoke(ScriptState* scriptState, const Dictionary& ra
wPermission) | 161 ScriptPromise Permissions::revoke(ScriptState* scriptState, const Dictionary& ra
wPermission) |
| 155 { | 162 { |
| 156 ExceptionState exceptionState(ExceptionState::GetterContext, "revoke", "Per
missions", scriptState->context()->Global(), scriptState->isolate()); | 163 ExceptionState exceptionState(ExceptionState::GetterContext, "revoke", "Per
missions", scriptState->context()->Global(), scriptState->isolate()); |
| 157 Nullable<WebPermissionType> type = parsePermission(scriptState, rawPermissio
n, exceptionState); | 164 Nullable<PermissionName> name = parsePermission(scriptState, rawPermission,
exceptionState); |
| 158 if (exceptionState.hadException()) | 165 if (exceptionState.hadException()) |
| 159 return exceptionState.reject(scriptState); | 166 return exceptionState.reject(scriptState); |
| 160 | 167 |
| 161 // This must be called after `parsePermission` because the website might | 168 // This must be called after `parsePermission` because the website might |
| 162 // be able to run code. | 169 // be able to run code. |
| 163 WebPermissionClient* client = getClient(scriptState->getExecutionContext()); | 170 PermissionService* service = getService(scriptState->getExecutionContext()); |
| 164 if (!client) | 171 if (!service) |
| 165 return ScriptPromise::rejectWithDOMException(scriptState, DOMException::
create(InvalidStateError, "In its current state, the global scope can't revoke p
ermissions.")); | 172 return ScriptPromise::rejectWithDOMException(scriptState, DOMException::
create(InvalidStateError, "In its current state, the global scope can't revoke p
ermissions.")); |
| 166 | 173 |
| 167 ScriptPromiseResolver* resolver = ScriptPromiseResolver::create(scriptState)
; | 174 ScriptPromiseResolver* resolver = ScriptPromiseResolver::create(scriptState)
; |
| 168 ScriptPromise promise = resolver->promise(); | 175 ScriptPromise promise = resolver->promise(); |
| 169 | 176 |
| 170 client->revokePermission(type.get(), KURL(KURL(), scriptState->getExecutionC
ontext()->getSecurityOrigin()->toString()), new PermissionCallback(resolver, typ
e.get())); | 177 service->RevokePermission(name.get(), scriptState->getExecutionContext()->ge
tSecurityOrigin()->toString(), convertToBaseCallback(WTF::bind(&Permissions::tas
kComplete, wrapPersistent(this), wrapPersistent(resolver), name.get()))); |
| 171 return promise; | 178 return promise; |
| 172 } | 179 } |
| 173 | 180 |
| 174 ScriptPromise Permissions::requestAll(ScriptState* scriptState, const Vector<Dic
tionary>& rawPermissions) | 181 ScriptPromise Permissions::requestAll(ScriptState* scriptState, const Vector<Dic
tionary>& rawPermissions) |
| 175 { | 182 { |
| 176 ExceptionState exceptionState(ExceptionState::GetterContext, "request", "Pe
rmissions", scriptState->context()->Global(), scriptState->isolate()); | 183 ExceptionState exceptionState(ExceptionState::GetterContext, "request", "Pe
rmissions", scriptState->context()->Global(), scriptState->isolate()); |
| 177 std::unique_ptr<Vector<WebPermissionType>> internalPermissions = wrapUnique(
new Vector<WebPermissionType>()); | 184 Vector<PermissionName> internalPermissions; |
| 178 std::unique_ptr<Vector<int>> callerIndexToInternalIndex = wrapUnique(new Vec
tor<int>(rawPermissions.size())); | 185 Vector<int> callerIndexToInternalIndex; |
| 186 callerIndexToInternalIndex.resize(rawPermissions.size()); |
| 179 for (size_t i = 0; i < rawPermissions.size(); ++i) { | 187 for (size_t i = 0; i < rawPermissions.size(); ++i) { |
| 180 const Dictionary& rawPermission = rawPermissions[i]; | 188 const Dictionary& rawPermission = rawPermissions[i]; |
| 181 | 189 |
| 182 Nullable<WebPermissionType> type = parsePermission(scriptState, rawPermi
ssion, exceptionState); | 190 Nullable<PermissionName> name = parsePermission(scriptState, rawPermissi
on, exceptionState); |
| 183 if (exceptionState.hadException()) | 191 if (exceptionState.hadException()) |
| 184 return exceptionState.reject(scriptState); | 192 return exceptionState.reject(scriptState); |
| 185 | 193 |
| 186 // Only append permissions to the vector that is passed to the client if
it is not already | 194 // Only append permissions to the vector that is passed to the client if
it is not already |
| 187 // in the vector (i.e. do not duplicate permisison types). | 195 // in the vector (i.e. do not duplicate permisison types). |
| 188 int internalIndex; | 196 int internalIndex; |
| 189 auto it = internalPermissions->find(type.get()); | 197 auto it = internalPermissions.find(name.get()); |
| 190 if (it == kNotFound) { | 198 if (it == kNotFound) { |
| 191 internalIndex = internalPermissions->size(); | 199 internalIndex = internalPermissions.size(); |
| 192 internalPermissions->append(type.get()); | 200 internalPermissions.append(name.get()); |
| 193 } else { | 201 } else { |
| 194 internalIndex = it; | 202 internalIndex = it; |
| 195 } | 203 } |
| 196 callerIndexToInternalIndex->operator[](i) = internalIndex; | 204 callerIndexToInternalIndex[i] = internalIndex; |
| 197 } | 205 } |
| 198 | 206 |
| 199 // This must be called after `parsePermission` because the website might | 207 // This must be called after `parsePermission` because the website might |
| 200 // be able to run code. | 208 // be able to run code. |
| 201 WebPermissionClient* client = getClient(scriptState->getExecutionContext()); | 209 PermissionService* service = getService(scriptState->getExecutionContext()); |
| 202 if (!client) | 210 if (!service) |
| 203 return ScriptPromise::rejectWithDOMException(scriptState, DOMException::
create(InvalidStateError, "In its current state, the global scope can't request
permissions.")); | 211 return ScriptPromise::rejectWithDOMException(scriptState, DOMException::
create(InvalidStateError, "In its current state, the global scope can't request
permissions.")); |
| 204 | 212 |
| 205 ScriptPromiseResolver* resolver = ScriptPromiseResolver::create(scriptState)
; | 213 ScriptPromiseResolver* resolver = ScriptPromiseResolver::create(scriptState)
; |
| 206 ScriptPromise promise = resolver->promise(); | 214 ScriptPromise promise = resolver->promise(); |
| 207 | 215 |
| 208 WebVector<WebPermissionType> internalWebPermissions = *internalPermissions; | 216 Vector<PermissionName> internalPermissionsCopy(internalPermissions); |
| 209 client->requestPermissions(internalWebPermissions, KURL(KURL(), scriptState-
>getExecutionContext()->getSecurityOrigin()->toString()), | 217 service->RequestPermissions(std::move(internalPermissions), scriptState->get
ExecutionContext()->getSecurityOrigin()->toString(), UserGestureIndicator::proce
ssingUserGesture(), |
| 210 new PermissionsCallback(resolver, std::move(internalPermissions), std::m
ove(callerIndexToInternalIndex))); | 218 convertToBaseCallback(WTF::bind(&Permissions::batchTaskComplete, wrapPer
sistent(this), wrapPersistent(resolver), std::move(internalPermissionsCopy), std
::move(callerIndexToInternalIndex)))); |
| 211 return promise; | 219 return promise; |
| 212 } | 220 } |
| 213 | 221 |
| 222 PermissionService* Permissions::getService(ExecutionContext* executionContext) |
| 223 { |
| 224 if (!m_service && connectToService(executionContext, mojo::GetProxy(&m_servi
ce))) |
| 225 m_service.set_connection_error_handler(convertToBaseCallback(WTF::bind(&
Permissions::serviceConnectionError, wrapWeakPersistent(this)))); |
| 226 return m_service.get(); |
| 227 } |
| 228 |
| 229 void Permissions::serviceConnectionError() |
| 230 { |
| 231 m_service.reset(); |
| 232 } |
| 233 |
| 234 void Permissions::taskComplete(ScriptPromiseResolver* resolver, PermissionName n
ame, mojom::blink::PermissionStatus result) |
| 235 { |
| 236 if (!resolver->getExecutionContext() || resolver->getExecutionContext()->act
iveDOMObjectsAreStopped()) |
| 237 return; |
| 238 resolver->resolve(PermissionStatus::take(resolver, result, name)); |
| 239 } |
| 240 |
| 241 void Permissions::batchTaskComplete(ScriptPromiseResolver* resolver, Vector<Perm
issionName> names, Vector<int> callerIndexToInternalIndex, mojo::WTFArray<mojom:
:blink::PermissionStatus> results) |
| 242 { |
| 243 if (!resolver->getExecutionContext() || resolver->getExecutionContext()->act
iveDOMObjectsAreStopped()) |
| 244 return; |
| 245 |
| 246 // Create the response vector by finding the status for each index by |
| 247 // using the caller to internal index mapping and looking up the status |
| 248 // using the internal index obtained. |
| 249 HeapVector<Member<PermissionStatus>> result; |
| 250 result.reserveInitialCapacity(callerIndexToInternalIndex.size()); |
| 251 for (int internalIndex : callerIndexToInternalIndex) |
| 252 result.append(PermissionStatus::createAndListen(resolver->getExecutionCo
ntext(), results[internalIndex], names[internalIndex])); |
| 253 resolver->resolve(result); |
| 254 } |
| 255 |
| 214 } // namespace blink | 256 } // namespace blink |
| OLD | NEW |