New issue
Advanced search Search tips
Note: Color blocks (like or ) mean that a user may not be available. Tooltip shows the reason.

Issue 609305 link

Starred by 4 users

Issue metadata

Status: Archived
Owner: ----
Closed: Dec 2017
Cc:
Components:
EstimatedDays: ----
NextAction: ----
OS: Mac
Pri: 2
Type: Bug



Sign in to add a comment

Possible shared web push subscription endpoints between sites

Reported by ja...@onesignal.com, May 4 2016

Issue description

UserAgent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_11_4) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/50.0.2661.86 Safari/537.36

Steps to reproduce the problem:
We haven't been able to find steps to reproduce the issue, but the issue is recurring.

What is the expected behavior?

What went wrong?
We're not sure whether this is a bug with Chrome or a bug with our web push product, as we haven't been able to find steps to reproduce the issue, but this is what we're noticing:

After a visitor subscribes to web push notifications, we store the endpoint returned from PushManager.subscribe() (e.g. https://android.googleapis.com/gcm/send/f2D78SMl4Nc:APA91bHOrhe13io3OM3y67C8bfXNLgc2ehhv1guDMN6a3n9t0CI18m7Wef-i4ylpWHBzf4qQt1gbvg_y4pmKCy0wTUneK9haUwMPHlhC2oGjIl-G4MZ-47lMHd-XsjBnY_rq5CTvJ_Nn) remotely on our server. The end result we're seeing is that, across our system over time, a small percentage of subscribers from different websites are sharing endpoints in our system. The shared endpoints vary; a couple of users from different sites might share one particular endpoint, while other users from other sites share another particular endpoint. For one of our customer's sites, for example, 326 / 35,000 (1%) users have an endpoint that's shared by at least one other user from another site on our system. Each of the 326 cases involve sharing a different unique endpoint. In one case, an endpoint is shared across 5 users from 5 different sites. Because an endpoint is valid for only one Project Number and Server API Key, the other users that share an endpoint are marked as having a MismatchSenderId when sending messages to the shared endpoint with the site's Server API Key.

Code: This (https://github.com/one-signal/OneSignal-Website-SDK/blob/529563704ba33ac7c8283debc09361d5670de952/src/OneSignal.js#L1200) method actually calls PushManager.subscribe() (line 1207) and forwards the endpoint to our server (line 1259).

We're trying to understand the cause of this issue. For these problematic sites, here's how our service worker and PushManager.subscribe() play out:

1. Each site hosts two service worker JS files. However, we provide the contents of these service worker files for our customers, and the contents of both workers are always the same: "importScripts('https://cdn.onesignal.com/sdks/OneSignalSDK.js');". More in #7 about why there are two workers.
2. The service worker is always automatically registered when a new page session begins (a new tab to the site, but not if the page is refreshed on the same tab).
3. The service worker is always registered to the top-most root-level scope of the site. Sometimes we use the 'Service-Worker-Allowed: /' header to achieve this. This procedure makes any existing service worker at the same root-level scope redundant and uninstalls it.
4. We use self.skipWaiting() and clients.claim() to make sure the newly installed service worker becomes activated right away.
5. After a service worker is registered, we always call PushManager.subscribe() after. So after a new page session begins, we always automatically register a SW and call PushManager.subscribe() after. Note: We don't auto-prompt-and-subscribe on every site; these problematic sites happen to have the feature enabled.
6. We never call PushSubscription.unsubscribe() anywhere in our code.
7. Because our customers' service worker files always have identical contents (one line with importScripts ...), the service workers don't automatically update to our latest CDN version. To solve this, whenever the user begins a new page session (a new tab to the site), we check whether a new version is available, and if so, we register an alternate service worker. We swap between the two service worker files, registering the alternately-named file to force the updated SW to be installed.
8. We noticed that, for users from site A sharing the same endpoint with users from different sites B, C, D, E, we noticed that sites A, B, C, D, and E were all related. For example, they are all Russian-based sites.
9. The sites are managed by different accounts (as far as we know), and each site has a different manifest.json gcm_sender_id / Project Number.

Sorry for the info dump! We're open to any tips about what might be causing these issues! This has been happening steadily and consistently for a small percentage of users.

Did this work before? No 

Chrome version: 50.0.2661.86  Channel: stable
OS Version: OS X 10.11.4
Flash Version: Shockwave Flash 21.0 r0
 
Components: Blink>ServiceWorker

Comment 2 by horo@chromium.org, May 9 2016

Components: Blink>PushAPI

Comment 3 by peter@chromium.org, May 9 2016

Owner: joh...@chromium.org
Status: Assigned (was: Unconfirmed)
John, mind taking a look?
Same thing! After subscribing on one site and going to another with another manifest I have the same endpoint. After reloading the page I see popup with notification permission request and after allowing - the new valid endpoint

Comment 5 by peter@chromium.org, Aug 1 2016

johnme: friendly ping

Comment 6 by joh...@chromium.org, Aug 10 2016

Components: -Blink>ServiceWorker
Status: ExternalDependency (was: Assigned)
Sorry about the delay. I've gone through Chrome's subscription caching and the GCM server's token generation, and I can't see anything that could cause the same token to be returned to different origins.

Could it be that some of your client websites occasionally change their OneSignal AppID, and the next time the page tries to subscribe, PushManager.subscribe() returns the existing subscription endpoint, which gets sent to your server alongside the new AppId, and now you have 2 or more entries with the same subscription endpoint but different AppIds?

This might also explain why the sites tend to be related (although in the case of accidentally copy-pasting another site's AppId, they might not be). In such a case, if each AppId has a different sender ID, then presumably only the first subscription uploaded to your server would work, and subsequent ones would likely get MismatchSenderId if you use the sender ID associated with the new AppId (but it was registered with the sender ID associated with the old AppId).

And/or is it possible that somehow the locally stored userId gets lost, and hence OneSignalHelper.registerWithOneSignal registers a new player at the /players endpoint instead of using /players/:id/on_session to update the existing entry? Though that alone probably wouldn't explain them being from different sites.
Hi Jason, are you still seeing this?
Hey John,

Sorry about the delay. Thanks for previously taking the time to look through our code and think of some suggestions. 

In the last 5 months or so, we haven't had any complaints that caused us to look at this issue. Occasionally when checking apps, we are still seeing this issue occur at the same small percentages (< 1%, typically 0.3% or 0.1%) or a person's users. We haven't yet run a script to find out exactly how many apps this affects and the average % per app.

Regarding the first scenario of a site changing their app ID, if a website accidentally changed IDs for a very brief period of time, we would definitely get duplicate subscriptions, but they would have to change their app ID back to the original ID quickly, otherwise more and more users would have duplicated IDs and it wouldn't be a consistently small percentage. Users don't typically change their app IDs; most of the cases of changing app IDs comes from messing something up and wanting to start over, or switching to HTTPS, but these reasons affect only one site, not different sites.

If the user uses the same app ID, I believe either of our endpoints will check for duplicates and requesting to create a new player should silently return the same player (to prevent duplicates).

I'm afraid we haven't found other insights so far. This isn't currently a priority issue for us. We may find other insights while refactoring our code in the future. Thanks for all your help on this.

Comment 9 by joh...@chromium.org, Dec 16 2017

Cc: joh...@chromium.org
Owner: ----
Status: Archived (was: ExternalDependency)
Hi Jason, thanks for the additional details. I'm going to archive this bug for now, as it doesn't seem that there is much we can do for now. But please feel free to re-open it if you see new evidence of any problems here :)

Sign in to add a comment