[meta] Consider mitigations for push notification abuse by websites
Categories
(Core :: DOM: Push Subscriptions, enhancement, P2)
Tracking
()
People
(Reporter: bzbarsky, Unassigned)
References
(Depends on 3 open bugs)
Details
(Keywords: meta)
Comment 1•8 years ago
|
||
Comment 2•8 years ago
|
||
Updated•8 years ago
|
Comment 3•8 years ago
|
||
Comment 4•8 years ago
|
||
Comment 5•8 years ago
|
||
Comment 6•8 years ago
|
||
Comment 7•8 years ago
|
||
Comment 8•8 years ago
|
||
Comment 9•8 years ago
|
||
Comment 10•8 years ago
|
||
Comment 12•6 years ago
|
||
Comment 13•6 years ago
|
||
Comment 14•6 years ago
|
||
Comment 15•6 years ago
|
||
(In reply to Andrew Sutherland [:asuth] from comment #13)
Push notifications imply the ability to wake up a ServiceWorker when the
user isn't browsing the site. So the permission grant is doing (secret)
double-duty, hopefully setting the expectation that the website will be able
to do things in the background. This, of course, is not necessarily
entirely obvious, so some browsers (like Chrome) will display a notification
if a SW that received a "push" event fails to display its own notification
(and in a timely fashion). Based on brief research, I think the
notification will say "This site has been updated in the background." with
the origin labeled[1].Which is to say, I don't think granting the ability to dispatch "push"
notifications but hiding the notifications is a workable strategy based on
the current execution model. (One could of course create an exciting new
sub-genre of anti-virus software to rein in the worst excesses...)
Fair criticism. I will say though that the "This site has been updated in the background" prompt is a terrible solution to the problem as well, since I posit that users generally do not have a mental model suggesting that sites are things that can run in the background, based on how sites have always worked. (I am willing to relinquish my position if we ever find user research that shows that users think of sites the same way as they think of "applications" running on their devices.)
I still think there are ways to mitigate the abuse scenario with the model that I suggested. I spent some time thinking about how we would do that. I took inspiration from a "background app optimizer" feature that I have in my HTC Android customization on my phone (I wish I could tell you where the software actually comes from... :/ )
The way that it works is that it allows applications to send push notifications freely, and it monitors how frequently you interact with them. If it notices you never interact with an app's notifications for three days or longer, it automatically adds the application to a block list of "optimized" applications which aren't allowed to receive push notifications while in background. When you open the app again, it is removed from that list. This works extremely well in removing the annoying notifications from apps that I never want to use (e.g. things I opened once to deal with a ticket, etc.)
Borrowing from the same concept, Firefox could monitor which sites send you invisible push notifications while in the background and keep tabs on whether you end up using the sites or not for a defined period of time (e.g. 3 days). When it notices you haven't used such a chatty site for 3 days or longer, it can add the site to the list of "optimized sites to not run in background in order to save battery life" or some such which would be visible and possible to manage in the Notifications Sidebar and block further push notifications from being delivered to that site. We can also have other heuristics for highly abusive scenarios (e.g. a maximum invisible push notification quota per day, per hour and per minute for each website with similar treatments once they go over quota).
Of course, the unfortunate side of this model would be that we would still tell the user about sites running in the background, but at least not for every single push notification, so if a site only sends one or two of these notifications the user wouldn't be bothered with any such prompts. The good side of the prompts over what Chrome shows is that the prompts we would show are something that tells the user something useful (we're saving you battery life, and preventing an abusive website) rather than an informational non-sequitur the user can't do anything about (hey this thing just happened, and yeah that's it, carry on with your life).
Obviously a person with actual UX skills could put me to real shame in designing something that is actually decent here, I'm just trying to expand the Overton window in our discussion around this UI, not by any means suggesting what actual UI we should have here. :-)
Comment 16•6 years ago
•
|
||
I'm still concerned about the prospect of providing free delayed execution. But I think we could probably leverage your notification sidebar idea to deal with this.
The pipeline of states leading to a displayed desktop notification is:
- Site requests push notification permission.
- The permission is granted.
- Site sends push notification.
- ServiceWorker gets to run.
- Desktop notification may possibly be displayed (somewhere)
Right now, we stall things and require annoying user interaction at step 1. Your proposal is to let sites get to 5 but eventually we shut them down after we've detected abuse, lack of user interest, or explicit user dis-interest.
We could potentially let all sites get to step 3 for the first time, but not actually run the ServiceWorker (step 4) until the user has expressed positive interest by tapping on a notification thingy that says "example.com wants to send you a notification". Once they've expressed interest, we let the ServiceWorker run and see how things shake out, with a desktop notification potentially being displayed.
The obvious downside to this strategy is it's possible that:
a. The SW may take some time to run leading to latency while the user has to stare at it waiting for a notification to show up.
b. The site may no longer want to show a desktop notification and so there's nothing to show. For example, a calendar notification for an event now in the past or an email that's already been read, etc.
c. The site is a nefarious bad site and the user is now watching as nothing happens and the site just burns CPU mining bitcoin.
d. The user may be offline right now...
For 'a', well, we want the push notification handling to be fast and responsive, so if the user ends up deciding to penalize the site for having a slow/laggy SW, that's okay. For 'b', well, that's less good, but we can at least have granted the permission from user intent. Sites could also learn to show a desktop notification in this case. Step 'c' is a case where it could be good for the user to explicitly blocklist the site, and we could help this by informing them that the site ended up using CPU/battery for N minutes, but it's still weird UX. For 'd', I think the notification bar would need to display "you're offline, but see these next time?"
It would also be possible to put something in the notification bar once the permission had been requested and auto-granted (pipeline step 1). And it would also be possible to speculatively grant full permissions to run SW based on an overwhelming indication of use of the site per history/heuristics.
Comment 17•6 years ago
|
||
(In reply to :Ehsan Akhgari from comment #15)
Borrowing from the same concept, Firefox could monitor which sites send you invisible push notifications while in the background and keep tabs on whether you end up using the sites or not for a defined period of time (e.g. 3 days). When it notices you haven't used such a chatty site for 3 days or longer, it can add the site to the list of "optimized sites to not run in background in order to save battery life" or some such which would be visible and possible to manage in the Notifications Sidebar and block further push notifications from being delivered to that site.
Interestingly, I think this is similar to, but not quite the same as, the quota system we have today. Each origin has a limited number of background pushes, capped at 16, and based on the visit time...the more recent your last visit, the higher the quota. For each incoming push, we start a 3 second timer before notifying the service worker. When the timer fires, we check if there's at least one notification visible for the origin, and dock it if not. Once an origin burns through its quota, we "expire" the subscription, where we drop it on the server, but prevent the page from resubscribing (and don't fire the pushsubscriptionchange
event) until after the next time you visit the page.
It's fairly opaque, though, and neither users nor developers have much insight into it (by design). The only indication that you sent too many background pushes is...you don't get pushes anymore. It also penalizes sites that want to do the right thing, but take more than 3 seconds to handle the push
event: what if they're on mobile and want to fetch something before showing the notification? Conversely, since that quota is specific to push, we'll still wake up the worker for fetch
events, even if the site is being nefarious.
Comment 18•6 years ago
|
||
(In reply to Andrew Sutherland [:asuth] from comment #16)
I'm still concerned about the prospect of providing free delayed execution. But I think we could probably leverage your notification sidebar idea to deal with this.
The pipeline of states leading to a displayed desktop notification is:
- Site requests push notification permission.
- The permission is granted.
- Site sends push notification.
- ServiceWorker gets to run.
- Desktop notification may possibly be displayed (somewhere)
Right now, we stall things and require annoying user interaction at step 1. Your proposal is to let sites get to 5 but eventually we shut them down after we've detected abuse, lack of user interest, or explicit user dis-interest.
Yes, this is a good way to think about it. I think the key point that I would like to focus on is to challenge ourselves to try to imagine what it would take for us to completely remove the user from the position of being burdened with deciding which website is allowed or isn't allowed to show notifications, and instead do our best to make push notifications be good citizens in most cases and empower the user to deal effectively with the egregiously abusive ones.
We could potentially let all sites get to step 3 for the first time, but not actually run the ServiceWorker (step 4) until the user has expressed positive interest by tapping on a notification thingy that says "example.com wants to send you a notification". Once they've expressed interest, we let the ServiceWorker run and see how things shake out, with a desktop notification potentially being displayed.
The obvious downside to this strategy is it's possible that:
a. The SW may take some time to run leading to latency while the user has to stare at it waiting for a notification to show up.
b. The site may no longer want to show a desktop notification and so there's nothing to show. For example, a calendar notification for an event now in the past or an email that's already been read, etc.
c. The site is a nefarious bad site and the user is now watching as nothing happens and the site just burns CPU mining bitcoin.
d. The user may be offline right now...
There is another bad side effect too, which is, it may be too late to run the SW code itself, no? For example, for a chat application which writes your chat history into an IndexedDB in sequence, if we hold the SW from executing, and the user opens the site again later before its SW has had a chance to run in the background, the site JS code may end up writing things into the DB before the JS code from the push notification has had a chance to run.
(Perhaps this is a possibility that developers have to deal with anyway due to running out of browser imposed quotas today anyway, I'm not too sure.)
For 'a', well, we want the push notification handling to be fast and responsive, so if the user ends up deciding to penalize the site for having a slow/laggy SW, that's okay. For 'b', well, that's less good, but we can at least have granted the permission from user intent. Sites could also learn to show a desktop notification in this case. Step 'c' is a case where it could be good for the user to explicitly blocklist the site, and we could help this by informing them that the site ended up using CPU/battery for N minutes, but it's still weird UX. For 'd', I think the notification bar would need to display "you're offline, but see these next time?"
It would also be possible to put something in the notification bar once the permission had been requested and auto-granted (pipeline step 1). And it would also be possible to speculatively grant full permissions to run SW based on an overwhelming indication of use of the site per history/heuristics.
Yes indeed these are all options we could explore, depending on how much of a problem we consider running the SW code before prompting the user to be.
(In reply to Lina Cambridge (she/her) [:lina] from comment #17)
(In reply to :Ehsan Akhgari from comment #15)
Borrowing from the same concept, Firefox could monitor which sites send you invisible push notifications while in the background and keep tabs on whether you end up using the sites or not for a defined period of time (e.g. 3 days). When it notices you haven't used such a chatty site for 3 days or longer, it can add the site to the list of "optimized sites to not run in background in order to save battery life" or some such which would be visible and possible to manage in the Notifications Sidebar and block further push notifications from being delivered to that site.
Interestingly, I think this is similar to, but not quite the same as, the quota system we have today. Each origin has a limited number of background pushes, capped at 16, and based on the visit time...the more recent your last visit, the higher the quota. For each incoming push, we start a 3 second timer before notifying the service worker. When the timer fires, we check if there's at least one notification visible for the origin, and dock it if not. Once an origin burns through its quota, we "expire" the subscription, where we drop it on the server, but prevent the page from resubscribing (and don't fire the
pushsubscriptionchange
event) until after the next time you visit the page.It's fairly opaque, though, and neither users nor developers have much insight into it (by design). The only indication that you sent too many background pushes is...you don't get pushes anymore. It also penalizes sites that want to do the right thing, but take more than 3 seconds to handle the
push
event: what if they're on mobile and want to fetch something before showing the notification? Conversely, since that quota is specific to push, we'll still wake up the worker forfetch
events, even if the site is being nefarious.
Thanks, that is great to know. The fact that SWs have to deal with this scenario in their push handlers is good news to me since it may mean that if a browser decides to explore an alternative avenue based on some of these ideas in order to remove permission prompts for push notifications then maybe some web compat pain could be avoided.
Comment 19•6 years ago
|
||
Note that bug 1429016 is on file remove or extend the expiration on some notification telemetry (related to the prompt, saved permissions, and the notifications themselves). If you think these would be useful to extend, please let me know this week as a contributor attached a patch to remove them all.
Comment 20•6 years ago
|
||
We are working on this.
Updated•2 years ago
|
Comment 21•2 years ago
|
||
We shipped the mitigation in bug 1593644 in Fx72, right? For now I'll mark this as inactive (and not fixed as there are still some subitems).
Description
•