Search code examples
androidbroadcastreceiveralarmmanager

Android: Method in MainActivity works fine, running same method in MainActivity via BroadcastReceiver class gives null pointer


So I have this method in my MainActivity and it works fine normally.

public void DailyQuoteDatabaseAccess(){

SQLiteOpenHelper sqLiteOpenHelper = new SQLiteAssetHelper(this, DATABASE_NAME, null, DATABASE_VERSION);
SQLiteDatabase SqlDb = sqLiteOpenHelper.getReadableDatabase();
String rawQuery = "SELECT * FROM dailyQuoteTable ORDER BY RANDOM() LIMIT 1";
Cursor cursor = SqlDb.rawQuery(rawQuery, null);
DailyQuoteCursorAdapter DQCursorAdapter = new DailyQuoteCursorAdapter(this, cursor);
this.mDailyQuoteListView.setAdapter(DQCursorAdapter);
}

However, when I try to run it from my BroadcastReceiver class, it is accessed but the app crashes and I get the following error in log cat:

Process: com.myapps.dailyquotes, PID: 15024
java.lang.RuntimeException: Error receiving broadcast Intent { act=android.net.conn.CONNECTIVITY_CHANGE flg=0x4000010 (has extras) } in com.myapps.dailyquotes.TodaysQuoteAlarmReceiver@d63089d
at android.app.LoadedApk$ReceiverDispatcher$Args.lambda$-android_app_LoadedApk$ReceiverDispatcher$Args_52497(LoadedApk.java:1323)
at android.app.-$Lambda$aS31cHIhRx41653CMnd4gZqshIQ.$m$7(Unknown Source:4)
at android.app.-$Lambda$aS31cHIhRx41653CMnd4gZqshIQ.run(Unknown Source:39)
at android.os.Handler.handleCallback(Handler.java:790)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:164)
at android.app.ActivityThread.main(ActivityThread.java:6494)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:438)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:807)
Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'android.content.pm.ApplicationInfo android.content.Context.getApplicationInfo()' on a null object reference
at android.content.ContextWrapper.getApplicationInfo(ContextWrapper.java:152)
at com.readystatesoftware.sqliteasset.SQLiteAssetHelper.<init>(SQLiteAssetHelper.java:109)
at com.readystatesoftware.sqliteasset.SQLiteAssetHelper.<init>(SQLiteAssetHelper.java:129)
at com.myapps.dailyquotes.MainActivity.DailyQuoteDatabaseAccess(MainActivity.java:403)

This is my BroadcastReceiver class:

package com.myapps.dailyquotes;

import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;

public class TodaysQuoteAlarmReceiver  extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
MainActivity mainActivity = new MainActivity();
mainActivity.DailyQuoteDatabaseAccess();

}
}

The line it highlights in the DailyQuoteDatabaseAccess method in the MainActivity is this one:

SQLiteOpenHelper sqLiteOpenHelper = new SQLiteAssetHelper(this, DATABASE_NAME, null, DATABASE_VERSION);

I call this from MainActivity onCreate... it links to the TodaysQuoteAlarmReceiver:

 public void AlarmForQuote() {

    Calendar calendar = Calendar.getInstance();

    calendar.setTimeInMillis(System.currentTimeMillis());
    calendar.set(Calendar.HOUR_OF_DAY, 21);
    calendar.set(Calendar.MINUTE, 28);

    Calendar cur = Calendar.getInstance();

    if (cur.after(calendar)) {
        calendar.add(Calendar.DATE, 1);
    }

    mTodaysQuoteIntent = new Intent(this, 
 TodaysQuoteAlarmReceiver.class);
    int ALARM_ID = 10000;
    mTodaysQuotePendingIntent = PendingIntent.getBroadcast(
            this.getApplicationContext(), ALARM_ID, mTodaysQuoteIntent, 
 PendingIntent.FLAG_UPDATE_CURRENT);

    mNewTodaysQuote = (AlarmManager) getSystemService(ALARM_SERVICE);

    mNewTodaysQuote.setRepeating(AlarmManager.RTC_WAKEUP, calendar.getTimeInMillis(),
            AlarmManager.INTERVAL_DAY, mTodaysQuotePendingIntent);

}

Solution

  • Activity classes in Android are never created with the new operator. They are created by the system when fulfilling an intent. If you create an activity the way you are doing so, it will not have the proper context set. That's why when it goes to create the SQLiteAssetHelper, you get a null pointer.