зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1189685 - Part 1: Ensure that the state of all ServiceWorker instances is up to date when dispatching statechange events; r=bkelly
This commit is contained in:
Родитель
5273912012
Коммит
e2a80ec087
|
@ -101,16 +101,6 @@ ServiceWorker::PostMessage(JSContext* aCx, JS::Handle<JS::Value> aMessage,
|
|||
aRv = workerPrivate->SendMessageEvent(aCx, aMessage, aTransferable, Move(clientInfo));
|
||||
}
|
||||
|
||||
void
|
||||
ServiceWorker::QueueStateChangeEvent(ServiceWorkerState aState)
|
||||
{
|
||||
nsCOMPtr<nsIRunnable> r =
|
||||
NS_NewRunnableMethodWithArg<ServiceWorkerState>(this,
|
||||
&ServiceWorker::DispatchStateChange,
|
||||
aState);
|
||||
MOZ_ALWAYS_TRUE(NS_SUCCEEDED(NS_DispatchToMainThread(r)));
|
||||
}
|
||||
|
||||
} // namespace workers
|
||||
} // namespace dom
|
||||
} // namespace mozilla
|
||||
|
|
|
@ -55,13 +55,9 @@ public:
|
|||
void
|
||||
DispatchStateChange(ServiceWorkerState aState)
|
||||
{
|
||||
SetState(aState);
|
||||
DOMEventTargetHelper::DispatchTrustedEvent(NS_LITERAL_STRING("statechange"));
|
||||
}
|
||||
|
||||
void
|
||||
QueueStateChangeEvent(ServiceWorkerState aState);
|
||||
|
||||
#ifdef XP_WIN
|
||||
#undef PostMessage
|
||||
#endif
|
||||
|
|
|
@ -4212,6 +4212,42 @@ ServiceWorkerInfo::RemoveWorker(ServiceWorker* aWorker)
|
|||
mInstances.RemoveElement(aWorker);
|
||||
}
|
||||
|
||||
namespace {
|
||||
|
||||
class ChangeStateUpdater final : public nsRunnable
|
||||
{
|
||||
public:
|
||||
ChangeStateUpdater(const nsTArray<ServiceWorker*>& aInstances,
|
||||
ServiceWorkerState aState)
|
||||
: mState(aState)
|
||||
{
|
||||
for (size_t i = 0; i < aInstances.Length(); ++i) {
|
||||
mInstances.AppendElement(aInstances[i]);
|
||||
}
|
||||
}
|
||||
|
||||
NS_IMETHODIMP Run()
|
||||
{
|
||||
// We need to update the state of all instances atomically before notifying
|
||||
// them to make sure that the observed state for all instances inside
|
||||
// statechange event handlers is correct.
|
||||
for (size_t i = 0; i < mInstances.Length(); ++i) {
|
||||
mInstances[i]->SetState(mState);
|
||||
}
|
||||
for (size_t i = 0; i < mInstances.Length(); ++i) {
|
||||
mInstances[i]->DispatchStateChange(mState);
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
private:
|
||||
nsAutoTArray<RefPtr<ServiceWorker>, 1> mInstances;
|
||||
ServiceWorkerState mState;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
ServiceWorkerInfo::UpdateState(ServiceWorkerState aState)
|
||||
{
|
||||
|
@ -4228,9 +4264,8 @@ ServiceWorkerInfo::UpdateState(ServiceWorkerState aState)
|
|||
MOZ_ASSERT_IF(mState == ServiceWorkerState::Activated, aState == ServiceWorkerState::Redundant);
|
||||
#endif
|
||||
mState = aState;
|
||||
for (uint32_t i = 0; i < mInstances.Length(); ++i) {
|
||||
mInstances[i]->QueueStateChangeEvent(mState);
|
||||
}
|
||||
nsCOMPtr<nsIRunnable> r = new ChangeStateUpdater(mInstances, mState);
|
||||
MOZ_ALWAYS_TRUE(NS_SUCCEEDED(NS_DispatchToMainThread(r.forget())));
|
||||
}
|
||||
|
||||
ServiceWorkerInfo::ServiceWorkerInfo(ServiceWorkerRegistrationInfo* aReg,
|
||||
|
|
Загрузка…
Ссылка в новой задаче