1

I'm using gcm for chat, and I have an onMessageReceived() method that receives the messages, saves them in the database, and sends a notification to the user.

When the app is running (or paused - running in the background), this is how I store the messages in the database:

private DBHelper mDbHelper;
mDbHelper = new DBHelper(MainApplication.getAppContext());
SQLiteDatabase db = mDbHelper.getWritableDatabase();

The method getAppContext() is a static method in my main activity which returns the context.

This all works. I receive a message, save it successfully, and get a notification (when app is running, or in the background).

Problem is when the app is closed. I can't use MainApplication.getAppContext();, because there's no context when the app is closed.

Maybe I should pass the context in some other way?


UPDATE

Eventually I saved messages on server if the app was closed, and when user opens it I fetch'em from server, delete them from there, and save them on user's device. (like a queue pop operation...)

Let me know if there's a better method
see accepted answer...

Alaa M.
  • 4,961
  • 10
  • 54
  • 95

3 Answers3

2

OK so 1 year later I needed this again and I found the answer:

Turns out there's a static method in SQLiteOpenHelper which opens the database without context: openDatabase().

So replace this:

mDbHelper = new DBHelper(MainApplication.getContext());
db = mDbHelper.getWritableDatabase();

with this:

db = SQLiteDatabase.openDatabase("path/to/database.db", null, OPEN_READWRITE);

The static method openDatabase() doesn't need a context so we can call it even when the app is closed.

Alaa M.
  • 4,961
  • 10
  • 54
  • 95
0

Create a class which extends Service and do your database operations in onStartCommand() method. Also start the service in onMessageReceived.

userDroid
  • 198
  • 9
0

For your need you can make use of broadcast receiver.

first, create a broadcast receiver like below,

public class UpdateReceiver extends BroadcastReceiver {

    protected UpdateListener listener;

    public UpdateReceiver(UpdateListener listener) {

        this.listener = listener;
    }

    @Override
    public void onReceive(Context context, Intent intent) {

        if (intent == null || intent.getExtras() == null) {
            return;
        }
        if (intent.getBooleanExtra("message", false)) {
            listener.onMessage(intent.getStringExtra("messageText"));
        } 
    }

    public interface UpdateListener {


        public void onMessage(String message);

    }
}

then make your MainActivity implement this receiver, like

public class MainActivity implements UpdateReceiver.UpdateListener

and you need to register your broadcast receiver, then you can override onMessage method in your MainActivity and you can receive your message there.

so your main activity will look like,

public class MainActivity  implements UpdateReceiver.UpdateListener {



    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        UpdateReceiver  chatMessageReceiver = new UpdateReceiver (this);
            registerReceiver(chatMessageReceiver, new       IntentFilter("messagereceived"));



    }

@Override
    protected void onMessage( String message) {

//do your DB Operations

    }

}

in your onMessageReceived method, call this broadcast receiver like,

        Intent intent = new Intent();
        intent.setAction("messagereceived");
        intent.putExtra("message", true);
        intent.putExtra("messageText", "your message")
        getApplicationContext().sendBroadcast(intent);
Basim Sherif
  • 5,384
  • 7
  • 48
  • 90
  • When the app is running I receive messages no matter what activity I'm in (I used `LocalBroadcastManager`). I save them successfully and send notifications. Problem is only when the app is closed. Will this solve the problem? Again, I do **receive** the messages - just can't save them. – Alaa M. Aug 14 '15 at 12:18
  • check my edited answer, this broadcast receiver will trigger whenever a message is received and you can save your message to DB, whether the app is in background or killed. – Basim Sherif Aug 14 '15 at 12:22
  • Again, I already have such a receiver. It's working. But I just can't use `DBHelper(Context context)` – Alaa M. Aug 14 '15 at 12:23
  • did you try passing getBaseContext() from your service? – Basim Sherif Aug 14 '15 at 12:25
  • Yes. Keeps failing on `super(context, DB_NAME, null, DB_VERSION);` in `DBHelper(Context context)` – Alaa M. Aug 14 '15 at 12:37
  • I tried your updated answer - the `BroadcastReceiver` doesn't get activated when I open the app... I guess the only way in this case is just to save the messages on the server and not on the phone. – Alaa M. Aug 20 '15 at 18:41