Skip to content

fix: create unsubscribed subscription for opted-out user when migrating#1430

Open
sherwinski wants to merge 5 commits intomainfrom
fix/create-not-subscribed-user-on-migration
Open

fix: create unsubscribed subscription for opted-out user when migrating#1430
sherwinski wants to merge 5 commits intomainfrom
fix/create-not-subscribed-user-on-migration

Conversation

@sherwinski
Copy link
Contributor

@sherwinski sherwinski commented Feb 27, 2026

Description

1 Line Summary

Create a new Subscription with the status "Not Subscribed" when migrating an opted-out user between one app ID and another.

Details

Previously, the SDK would skip creating any subscription on app ID2 when migrating from app ID1 if the subscription was opted-out at the time of migration. Now, the SDK will create a new Subscription with the status "Not Subscribed" on app ID2.

This could be achieved by creating a "Subscribed" subscription and then immediately updating it to "Opted Out", which requires two server operations. Instead, this PR updates the logic to thread a notificationTypesOverride parameter through registerForPush_subscribeupdatePushSubscriptionModelWithRawSubscription so that CreateSubscriptionOperation is sent with notification_types = -2 (UserOptedOut) from the start.

This results in a single server operation and avoids any transient intermediary states.

App 1 App 2 (after migration)
Screenshot 2026-02-27 at 9 18 50 PM Screenshot 2026-02-27 at 9 20 25 PM

Systems Affected

  • WebSDK
  • Backend
  • Dashboard

Validation

Tests

Info

Checklist

  • All the automated tests pass or I explained why that is not possible
  • I have personally tested this on my machine or explained why that is not possible
  • I have included test coverage for these changes or explained why they are not needed

Programming Checklist
Interfaces:

  • Don't use default export
  • New interfaces are in model files

Functions:

  • Don't use default export
  • All function signatures have return types
  • Helpers should not access any data but rather be given the data to operate on.

Typescript:

  • No Typescript warnings
  • Avoid silencing null/undefined warnings with the exclamation point

Other:

  • Iteration: refrain from using elem of array syntax. Prefer forEach or use map
  • Avoid using global OneSignal accessor for context if possible. Instead, we can pass it to function/constructor so that we don't call OneSignal.context

Screenshots

Info

Checklist

  • I have included screenshots/recordings of the intended results or explained why they are not needed

Related Tickets



This change is Reviewable

Previously, the SDK would skip creating any subscription on app ID2 when migrating from app ID1 if the subscription was opted-out at the time of migration. Now, the SDK will create a new Subscription with the status "Not Subscribed" on app ID2.

This could be achieved by creating a "Subscribed" subscription and then immediately updating it to "Opted Out", which requires two server operations. This commit updates the logic to thread a `notificationTypesOverride` parameter through `registerForPush` →
`_subscribe` → `updatePushSubscriptionModelWithRawSubscription` so the
`CreateSubscriptionOperation` is sent with notification_types = -2
(UserOptedOut) from the start. This results in a single server
operation and avoids any transient intermediary states.
@sherwinski sherwinski force-pushed the fix/create-not-subscribed-user-on-migration branch from 299715f to d6f420c Compare February 27, 2026 13:52
Update `createOptedOutSubscriptionForMigration` to call `_subscribe()` directly instead of `registerForPush()`. This creates the model with `_UserOptedOut` and calls `createUserOnServer()` to send the `CreateSubscriptionOperation` with the correct state, without triggering the `_registerSubscription` and `checkAndTriggerSubscriptionChanged` steps that fight against the opted-out state.
Comment on lines +419 to +422
await OneSignal._context._subscriptionManager._subscribe(
SubscriptionStrategyKind._ResubscribeExisting,
NotificationType._UserOptedOut,
);
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Open to suggestions if there's a better way to achieve this.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant