Bug 1879112 - Check permission earlier and mark as closed if failed r=asuth

Differential Revision: https://phabricator.services.mozilla.com/D201140
This commit is contained in:
Kagami Sascha Rosylight 2024-04-22 16:59:56 +00:00
parent 90f3cc99ef
commit d96e4fdf00
2 changed files with 27 additions and 5 deletions

View File

@ -1317,6 +1317,8 @@ bool Notification::IsInPrivateBrowsing() {
return false; return false;
} }
// Step 4 of
// https://notifications.spec.whatwg.org/#dom-notification-notification
void Notification::ShowInternal() { void Notification::ShowInternal() {
AssertIsOnMainThread(); AssertIsOnMainThread();
MOZ_ASSERT(mTempRef, MOZ_ASSERT(mTempRef,
@ -1331,13 +1333,15 @@ void Notification::ShowInternal() {
std::swap(ownership, mTempRef); std::swap(ownership, mTempRef);
MOZ_ASSERT(ownership->GetNotification() == this); MOZ_ASSERT(ownership->GetNotification() == this);
nsresult rv = PersistNotification();
if (NS_FAILED(rv)) {
NS_WARNING("Could not persist Notification");
}
nsCOMPtr<nsIAlertsService> alertService = components::Alerts::Service(); nsCOMPtr<nsIAlertsService> alertService = components::Alerts::Service();
// Step 4.1: If the result of getting the notifications permission state is
// not "granted", then queue a task to fire an event named error on this, and
// abort these steps.
//
// XXX(krosylight): But this function is also triggered by
// Notification::ShowPersistentNotification which already does its own
// permission check. Can we split this?
ErrorResult result; ErrorResult result;
NotificationPermission permission = NotificationPermission::Denied; NotificationPermission permission = NotificationPermission::Denied;
if (mWorkerPrivate) { if (mWorkerPrivate) {
@ -1358,13 +1362,28 @@ void Notification::ShowInternal() {
} else { } else {
DispatchTrustedEvent(u"error"_ns); DispatchTrustedEvent(u"error"_ns);
} }
mIsClosed = true;
return; return;
} }
// Preparing for Step 4.2 the fetch steps. The actual work happens in
// nsIAlertNotification::LoadImage
nsAutoString iconUrl; nsAutoString iconUrl;
nsAutoString soundUrl; nsAutoString soundUrl;
ResolveIconAndSoundURL(iconUrl, soundUrl); ResolveIconAndSoundURL(iconUrl, soundUrl);
// Step 4.3 the show steps, which are almost all about processing `tag` and
// then displaying the notification. Both are handled by
// nsIAlertsService::ShowAlert/PersistentNotification. The below is all about
// constructing the observer (for show and close events) right and ultimately
// call the alerts service function.
// XXX(krosylight): Non-persistent notifications probably don't need this
nsresult rv = PersistNotification();
if (NS_FAILED(rv)) {
NS_WARNING("Could not persist Notification");
}
bool isPersistent = false; bool isPersistent = false;
nsCOMPtr<nsIObserver> observer; nsCOMPtr<nsIObserver> observer;
if (mScope.IsEmpty()) { if (mScope.IsEmpty()) {

View File

@ -776,6 +776,9 @@ ToastNotification::CloseAlert(const nsAString& aAlertName,
bool aContextClosed) { bool aContextClosed) {
RefPtr<ToastNotificationHandler> handler; RefPtr<ToastNotificationHandler> handler;
if (NS_WARN_IF(!mActiveHandlers.Get(aAlertName, getter_AddRefs(handler)))) { if (NS_WARN_IF(!mActiveHandlers.Get(aAlertName, getter_AddRefs(handler)))) {
// This can happen when the handler is gone but the closure signal is not
// yet reached to the content process, and then the process tries closing
// the same signal.
return NS_OK; return NS_OK;
} }