Onesignal-ios-sdk: Crash on setEmail:

Created on 28 May 2019  路  20Comments  路  Source: OneSignal/OneSignal-iOS-SDK

Description:
We have this crash happening in production. Hasn't happened to us while debugging.

Environment

  1. SDK Version: v2.9.5 (just bumped to latest to see if it'll make any difference. I don't find this issue on the change log)
  2. Cocoapods v1.6

Steps to Reproduce Issue:
Unknown - happened in production only

Fatal Exception: NSInvalidArgumentException
* -[__NSPlaceholderDictionary initWithObjects:forKeys:count:]: attempt to insert nil object from objects[0]

Fatal Exception: NSInvalidArgumentException
0 CoreFoundation 0x1af7fb3d __exceptionPreprocess
1 libobjc.A.dylib 0x1a207067 objc_exception_throw
2 CoreFoundation 0x1ae97485 -[__NSPlaceholderDictionary initWithObjects:forKeys:count:]
3 CoreFoundation 0x1ae972ef +[NSDictionary dictionaryWithObjects:forKeys:count:]
4 FotoSprint 0x4140d1 +[OSRequestCreateDevice withAppId:withDeviceType:withEmail:withPlayerId:withEmailAuthHash:] (Requests.m:148)
5 FotoSprint 0x3fbd53 +[OneSignal setEmail:withEmailAuthHashToken:withSuccess:withFailure:] (OneSignal.m:2190)
6 FotoSprint 0x3fc2d5 +[OneSignal setEmail:withSuccess:withFailure:] (OneSignal.m:2223)
7 FotoSprint 0x3fc7c7 +[OneSignal setEmail:] (OneSignal.m:2264)
8 FotoSprint 0xe203b specialized Analytics.identifyUser() (Analytics.swift:32)

Possible Bug

All 20 comments

Hello,
Thanks for your patience. Would you mind including the code snippet where you are making the call? Also, how widespread is this issue?

We have 24 instances of it in the last 30 days in an app with about 20k monthly sessions. Now that I'm analyzing the logging, I think it might be a race condition where OneSignal is not yet initialized. We had to defer a bunch of the app initialization from application:didFinishLaunchingWithOptions: until the next runloop iteration a few versions ago, but it seems applicationDidBecomeActive: is sometimes, very rarely, squeezing in between. I'll move OneSignal's initialization back since it's probably harmless time wise and report back. However, internal validation would be nice so the error is more readable. It might happen to someone without as much logging to figure out it.

Interesting. Thanks for the details. Please, let us know your findings and we'll make a note of this issue so we can try to provide better error logging

I'm actually facing the same problem in here. I've moved OneSignal's initialization to a class that is injected and then called synchronously in application:didFinishLaunchingWithOptions: It is supposed to be working. There is actually 40 instances of this crash in a week of my application's phased released. I'm wondering if there is anyway to check whether the SDK is initialized?

@viniciusromani ,
Take a look at our logging method. It should tell you info such as if the SDK was initialized correctly.

@rgomezp I was just wondering if I could do something:
if OneSignal.isInitialized { OneSignal.setEmail("[email protected]") }

Before I do OneSignal.setEmail() method call I actually check whether the email I am passing as parameter is not nil and is not empty. Do you have any other suggestion to shut the crash down ?

@viniciusromani ,
OneSignal does not have a isInitialized member. Is this something you found somewhere? However, it is a good idea to check that the email you are passing into setEmail isn't nil.

@rgomezp yeah, yeah. That was just a little insight I had to prevent the crash from happen. I don't see what I am doing wrong so I was just trying to figure out something to prevent it :) Do you guys have any idea why this start to happen?
I was using an old version of the SDK (2.0 - yeah! very old) and it started to happen when I update it to the 2.10 version.

I'm not sure why it started happening. Will have to do some digging. However, did checking for nil fix the issue temporarily?

Nope, the underlying method signature is

[OSRequestCreateDevice withAppId:withDeviceType:withEmail:withPlayerId:withEmailAuthHash:]

If we assume it is a framework race condition issue, I suspect either appId or playerId params are the cause of the crash. The email I ensure it is not nil and even not empty, the authHash is optional so, for elimination those are the one that could be causing the crash. It is just an assumption :)

Do you think it is a good practice to have some thing like if OneSignal.playerId != nil before calling OneSignal.setEmail ? I wonder whether the solution would not generate any side effect like not setting the email or something like that?

PS. We use OneSignal for push notifications :)

Ok. the release with the change has gone live today. I will report in a few days whether it made a difference.

@viniciusromani ,
That sounds like a good idea. You can check to make sure that the playerId is not null before setting it

@fer662 ,
Looking forward to it!

So, nice news for everyone :) Our release is about to go live too, it might be available by the end of the week so, one more report is freshly new as well

I cannot set the email of the user, but I can set any other tag or even the external id. I don't know what i'm doing wrong.

  OneSignal.setEmail(email) // This doens't update the email of my user in OneSignal
  OneSignal.setExternalUserId(userId) // This works as expected

@Dfmarulanda , please use the logging method to gain further insight into what's happening

After 8 days there are no instances of the crash anymore. I suggest that people having the issue try to keep the OneSignal initialization as simple as possible or add a locking mechanism on your side to ensure it's initialized before you use it.

@rgomezp

VERBOSE: HTTP Request (OSRequestCreateDevice) with URL: https://onesignal.com/api/v1/players, with parameters: {
  "email_auth_hash" : null,
  "device_player_id" : "ea73ebc2-1a47-42a0-be71-88b002c7350f",
  "app_id" : "47261457-85c1-4ed7-b391-85b497f4513a",
  "identifier" : "[email protected]",
  "device_type" : 11

NSLocalizedDescription=Se ha producido un error de SSL y no puede establecerse una conexi贸n segura con el servidor., NSErrorFailingURLKey=https://onesignal.com/api/v1/apps/47261457-85c1-4ed7-b391-85b497f4513a/ios_params.js?player_id=ea73ebc2-1a47-42a0-be71-88b002c7350f, NSUnderlyingError=0x28047cd50 {Error Domain=kCFErrorDomainCFNetwork Code=-1200 "(null)" 

@Dfmarulanda
Can you try to pass into the function an email auth hash?

Take a look at our docs for more info

Closing due to no response

We have met the same issue. In OneSignal version 2.13.1. OneLink.setEmail() method gives exception
Fatal Exception: NSInvalidArgumentException *** -[__NSPlaceholderDictionary initWithObjects:forKeys:count:]: attempt to insert nil object from objects[0]

But, if you call fucntion +(void)setEmail:(NSString * _Nonnull)email withEmailAuthHashToken:(NSString * _Nullable)hashToken;, everything works fine with no exceptions.

Was this page helpful?
0 / 5 - 0 ratings