PARSE: Push Notifications "deviceToken" undefined

10,056

Solution 1

Are you using 2 user profiles at the same time on the tablet? Because I've had exactly the same problem and from my experience there is a conflict between the profiles. Infact, in my situation one device was registering 2 rows into the Parse database. One with the deviceToken and one with "undefined" deviceToken.

Unfortunately I've never solved this problem, I guess this is a bug from Parse.

Solution 2

It could be useful to set parse logging to verbose to help debug further:

Parse.setLogLevel(Parse.LOG_LEVEL_VERBOSE);

With that I noticed that I was using the wrong "sender_id" in my manifest:

<meta-data android:name="com.parse.push.gcm_sender_id"
    android:value="id:123456789"/>

That might not be the exact solution, but LOG_LEVEL_VERBOSE might help debug this.

Solution 3

I had been struggling with this problem for a long time until I recently realized what has been going on. Not only does the package name need to match, but you also need to include the build flavor in your declaration.

If you followed the parse tutorial and replace com.parse.starter with your package name, you are done if you have no build flavor, but if you do you need to make sure to include that as such:

com.packagename.build_flavor{debug, release, etc.}

Solution 4

Some installations do have a GCM Registration Id set up in their deviceToken column, which is a good indication that your setup is correct. Is it definitely possible for an installation to lack a GCM Registration Id:

  • The device may not have access to Google Services Framework (e.g. Amazon Kindle Fire). If you have set up the non-GCM ParsePush receiver, pushes to these devices should still get delivered.
  • The app has been deleted from the device, and thus it has been unregistered from GCM. We do not automatically delete installations in this case as that could potentially lead to unintended data loss, given that you're allowed to store arbitrary data in your installation class.
  • Google Services Framework may have been unavailable when the device attempted to register itself.

In the first two scenarios, this is working as expected and it's not something to generally worry about.

Share:
10,056

Related videos on Youtube

ernestocattaneo
Author by

ernestocattaneo

Updated on August 31, 2020

Comments

  • ernestocattaneo
    ernestocattaneo almost 4 years

    This is the situation in my Installation page on Parse Console:

    enter image description here

    As you see some devices have the "deviceToken" and some do not have the "deviceToken". This is not good because every device should have the deviceToken in order to work.

    How is this possible? This is a serious problem because the ones that do not have the deviceToken do not receive push notifications!

    I've followed all the instructions on Parse.com and implemented everything as they said, even with the help of their blank project and with the help of various questions on the web. But nothing fixed my problem and now I can't do anything.

    The only thing I can think about is that before my application (it is already on the Store) used to use Google Cloud Messaging and then with this new update I've decided to change the system and use Parse removing completely GCM system. Is there maybe a conflict between the two systems?

    I need to fix this as you can imagine this is a serious bug and now 3/4 of my users do not receive push notifications.

    If you download the app and install it: everything is good, the deviceToken is ok. If you update the app because there already was a version with GCM on the device:

    • some devices register in Parse good, without any problem
    • some devices register in Parse but without the deviceToken

    For the devices that do not have the deviceToken I've tried a lot of things: inserting a deviceToken manually, uninstall and reinstall the application, delete the specific row on Parse, etc. But nothing good... Still facing this problem.

    MY CODE

    Application.java

    public class Application extends android.app.Application {
    
    public Application() {
    }
    
    @Override
    public void onCreate() {
        super.onCreate();
    
        // Initialize the Parse SDK.
        Parse.initialize(this, "x", "x");
    
        // Specify an Activity to handle all pushes by default.
        PushService.setDefaultPushCallback(this, MainActivity.class);
    
    }
    

    }

    MainActivity.java In my mainActivity I just concatenate the deviceToken (in my case it is the installationId) into my userAgent: and this work fine: I always have the installationId without any problem! And this is the only thing I am doing in my MainActivity (do I need to do anything else? saveInBackground, callback, etc..?)

    deviceToken = ParseInstallation.getCurrentInstallation().getInstallationId();
    webSettings.setUserAgentString(userAgent + " ||" + deviceToken);
    

    AndroidManifest.xml

    <!-- Gestione del guasto-->
    <uses-permission android:name="android.permission.CAMERA" />
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
    <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
    
    <!-- Utilizzo di internet  -->
    <uses-permission android:name="android.permission.INTERNET" />
    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
    
    <!-- Permesso di vibrare per le push notifications -->
    <uses-permission android:name="android.permission.VIBRATE" />
    
    
    <uses-permission android:name="android.permission.GET_ACCOUNTS" />
    
    <!-- Mantiene attivo il processore così da poter ricevere in qualsiasi momento le notifiche -->
    <uses-permission android:name="android.permission.WAKE_LOCK" />
    
    <!-- Consente di impostare l'allarme per l'aggiornamento automatico -->
    <uses-permission android:name="com.android.alarm.permission.SET_ALARM"/>
    
    
    <permission android:name="com.hoxell.hoxellbrowser.permission.C2D_MESSAGE"
        android:protectionLevel="signature" />
    <uses-permission android:name="com.hoxell.hoxellbrowser.permission.C2D_MESSAGE" />
    <uses-permission android:name="com.google.android.c2dm.permission.RECEIVE" />
    
    <application
        android:name="com.hoxell.hoxellbrowser.Application"
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher_hoxell"
        android:label="@string/app_name"
        android:theme="@style/AppTheme"
        >
    
        <!-- Richiesto per le applicazioni che usano Google Play Services -->
        <meta-data android:name="com.google.android.gms.version" android:value="@integer/google_play_services_version" />
    
        <activity
            android:name=".MainActivity"
            android:label="@string/app_name"
            android:configChanges="keyboardHidden|orientation|screenSize"
            android:windowSoftInputMode="adjustResize"
            android:launchMode="singleTask">
    
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
    
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    
        <activity
            android:name=".SettingsActivity"></activity>
    
        <receiver android:name=".AlarmReceiver"/>
    
    
        <service android:name="com.parse.PushService" />
        <receiver android:name="com.parse.ParseBroadcastReceiver">
            <intent-filter>
                <action android:name="android.intent.action.BOOT_COMPLETED" />
                <action android:name="android.intent.action.USER_PRESENT" />
            </intent-filter>
        </receiver>
        <receiver android:name="com.hoxell.hoxellbrowser.Receiver"
            android:exported="false">
            <intent-filter>
                <action android:name="com.parse.push.intent.RECEIVE" />
                <action android:name="com.parse.push.intent.DELETE" />
                <action android:name="com.parse.push.intent.OPEN" />
            </intent-filter>
        </receiver>
        <receiver android:name="com.parse.GcmBroadcastReceiver"
            android:permission="com.google.android.c2dm.permission.SEND">
            <intent-filter>
                <action android:name="com.google.android.c2dm.intent.RECEIVE" />
                <action android:name="com.google.android.c2dm.intent.REGISTRATION" />
    
                <category android:name="com.hoxell.hoxellbrowser" />
            </intent-filter>
        </receiver>
    
    </application>
    

    Build.gradle

    dependencies {
    compile fileTree(dir: 'libs', include: ['*.jar'])
    // You must install or update the Support Repository through the SDK manager to use this dependency.
    compile 'com.android.support:support-v4:20.+' //support
    compile "com.google.android.gms:play-services:5.0.+" //play services
    compile 'com.parse.bolts:bolts-android:1.+'
    compile fileTree(dir: 'libs', include: 'Parse-*.jar')
    

    }

    I don't really know what else to do, that's why I hope that somebody can help me with this.

    Thank you.

    • Héctor Ramos
      Héctor Ramos over 9 years
      FYI, the registration id is stored in the deviceToken column, not in installationId.
  • ernestocattaneo
    ernestocattaneo over 9 years
    this is not what I've asked
  • ernestocattaneo
    ernestocattaneo over 9 years
    The device has access to the Google Services Framework (galaxy tab 3).. and it is not a problem of unavailability… What I did with a device without the deviceToken was to manually delete and reinstall the application and a new registration has been made: but still without the deviceToken. I’ve tried clearing app cache/data, but same result. I don’t know what else to do… We do not want to leave Parse framework: we think it is amazing. But really.. what else can we do to solve our problem? Please help.. you are the only one that can actually help us.. :)
  • ernestocattaneo
    ernestocattaneo over 9 years
    I've added my Build.gradle code: is there maybe a problem concerning gms version compiling..?
  • ernestocattaneo
    ernestocattaneo over 9 years
    Damn, you're right. This is it. I do have 2 profiles in the tablet and I've just tested it: the normal profile does receive the deviceToken but the restricted one (the one I need!) does not receive it. Dammit! And now? Can I do anything?!?
  • WiTHS4UC3
    WiTHS4UC3 over 9 years
    As I said I did not solve this problem. Because of this, I used only 1 profile for 1 tablet
  • Kishore Jethava
    Kishore Jethava about 9 years
    which type of profile u talking , b'coz i m facing same issue.
  • Ziv Kesten
    Ziv Kesten almost 9 years
    I dont understand this answer, you say this is a reasonable behavior, but i don't understand why, i have this problem, no deviceToken and no type, this means my user cannot receive push, how can this be corrected?
  • Héctor Ramos
    Héctor Ramos almost 9 years
    If the user opted out of push notifications by deleting your app, there's no app to push to. Therefore, it is reasonable behavior :)
  • Héctor Ramos
    Héctor Ramos almost 9 years
    Similarly, GCM is only supported on devices with access to Google Services. A Kindle device wouldn't be able to obtain a registration token.
  • Hannan Shaik
    Hannan Shaik over 8 years
    was anyone able to solve this problem? I am also stuck at the same place.
  • Rafa0809
    Rafa0809 over 8 years
    You can add a new column in the parse installation table called "isActiveUser". An device can't have 2 sessions with different users in the same instant.