0

Context

I am trying to retrieve MMS data from Android, I can count the MMS from content://mms/ but when I want to get the MMS data then it's empty.

Problem

First I count the MMS like this:

Uri uri = Telephony.Mms.CONTENT_URI;  // content://mms/

Cursor cursor = contentResolver.query(uri, null, null, null, null);
int count = cursor.getCount();

Assuming I have 3 MMS, the count is equal to 3. No problem here.

Now I want to retrieve the data from each MMS, I found out (here and here) that I had to query the content://mms/part provider, that's what I did. The problem is that this cursor is always empty, I've tried many different ways:

Uri uri = Uri.parse("content://mms/part");
String selection = Telephony.Mms.Part.MSG_ID + " = " + id;
Cursor cursor = contentResolver.query(uri, null, selection, null, null);

// OR

Uri uri = Uri.parse("content://mms/part/" + id);
Cursor cursor = contentResolver.query(uri, null, null, null, null);

// OR

Uri uri = Uri.parse("content://mms/" + id "/part");
Cursor cursor = contentResolver.query(uri, null, null, null, null);

And each time, my cursor is empty.


Getting MMS id:

Cursor cursor= contentResolver.query(Telephony.Mms.CONTENT_URI, new String[]{"*"}, null, null, null);
if (cursor!= null) {
    if (cursor.getCount() > 0) {
        cursor.moveToFirst();
        while (!cursor.isAfterLast()) {
            sms = createMmsFromCursor(cursor);
            cursor.moveToNext();
        }
        cursor.close();
    }
}

And then the createMmsFromCursor(cursor):

private final MMS createMmsFromCursor(Cursor cursor) {
    long id = cursor.getLong(cursor.getColumnIndex(Telephony.Mms._ID));
    // ...
    Map.Entry partValues = getDataFromMms(id);
    // ...
    return mms;
}

The getDataFromMms(id) will call the above code (where my problem is) using the id given in parameter.

Question

Am I correctly querying the content provider ? Or am I using the wrong provider Uri ? Maybe the MMS part Uri is different depending on the device, if so, how can I always point on the right Uri ?

Community
  • 1
  • 1
megaturbo
  • 680
  • 6
  • 24
  • Your first version, at least, should work. Are you certain `id` is valid? How are you getting its value? – Mike M. Jan 17 '17 at 14:58
  • I use the `content://mms/` provider to get each MMS basic information and retrieve id with: `cursor.getLong(cursor.getColumnIndex(Telephony.Mms._ID));` I will update question – megaturbo Jan 17 '17 at 15:16
  • @MikeM. There I showed how I get the `id` – megaturbo Jan 17 '17 at 15:33
  • Hmm, everything seems OK, at first glance. You might try querying the part URI with a null selection, and use a `DatabaseUtils.dumpCursor*()` method to see what you get; at least make sure something's there. – Mike M. Jan 17 '17 at 15:53
  • Thanks for the `DatabaseUtils` method I wasn't aware of that. So if I create my cursor on `content://mms/part` with a null selection it doesn't loop **but** the `dumpCursor` out 3 times : `Dumping cursor android.content. ...` What does that mean, if it's not empty, but doesnt loop, also `getCount()` returns `0` ? – megaturbo Jan 18 '17 at 07:53
  • The `Dumping cursor...` header will show even if it's empty. What follows that line? If there are any records, they'll be printed like `0 { _id=319 mid=131 ... } 1 { _id=320 mid=133 ... } ...`, but with more columns, each on it's own line. – Mike M. Jan 18 '17 at 08:07
  • The first one look like this `Dumping cursor android.content.ContentResolver$CursorWrapperInner@8d89116` and the id is different for each – megaturbo Jan 18 '17 at 08:08
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/133417/discussion-between-mike-m-and-thomas-roulin). – Mike M. Jan 18 '17 at 08:09
  • 1
    @MikeM. Please excuse me for wasting your time. Apparently the APN of the phone I used was wrongly configured... I reset the MMS APN and now it's working. At least the `dumpCursor` show the content. Now that you look familiar with SO, should I close this question or answer it with something like "reset APN" ? – megaturbo Jan 18 '17 at 10:55
  • And so you were telling me, that if I set my app as the default SMS/MMS app I have to handle the storage of the MMS, right ? – megaturbo Jan 18 '17 at 15:46
  • Ah, I didn't even think of that possibility. Well, glad you figured it out. Yeah, the default messaging app is responsible for saving all incoming, and its own outgoing, messages. MMS is kind of a pain, 'cause it's not nearly as simple as handing SMS. There are libraries available to deal with MMS, if you don't want to roll your own. As for keeping this question, I'd say yeah, do. I've not come across this situation before, and I keep an eye on most of the SMS/MMS posts that come through here. – Mike M. Jan 18 '17 at 17:28
  • Ok I will have a look on how to do that. I will keep this question up. And yes, I've come across many answers from you when I was looking for information, you already helped me. – megaturbo Jan 19 '17 at 10:10

1 Answers1

0

Not sure if you have found an answer yet. Here is what I have, and it is working (for me):

Uri uriMms = Uri.parse("content://mms/");
final String[] projection = new String[]{"*"};
Cursor cursor = contentResolver.query(uriMms, projection, null, null, null);
String id = cursor.getString(cursor.getColumnIndex("_id"));
String selectionPart = "mid=" + id;
Uri uri = Uri.parse("content://mms/part");
Cursor cursor2 = getContentResolver().query(uri, null, selectionPart, null, null);

Then do cursor2.moveToFirst()

Kevin
  • 465
  • 6
  • 12