开发者

How to use SMS content provider? Where are the docs?

I'd like to be able to read the system's SMS content provider. Basically I wanted to make an SMS messaging app, but it would only be useful if I could see past threads etc.

It seems like there's a content provider for this, but I can't find documentation for it - anyone know where that is?

Thanks

-------- edit -----------

Ok I found a way to get the sms inbox provider, and I just dumped all the column nam开发者_Go百科es in that provider, looks like this:

Uri uriSms = Uri.parse("content://sms/inbox");
Cursor c = context.getContentResolver().query(uriSms, null,null,null,null); 

// column names for above provider:
0: _id
1: thread_id
2: address
3: person
4: date
5: protocol
6: read   
7: status
8: type
9: reply_path_present
10: subject
11: body
12: service_center
13: locked

I'm just piecing this together from random threads I find around the net, I'm really wondering where this is all documented (if at all)?

Thanks again


In addition to those u can see the list of fields in sms content provider by using following code:

private void displaySmsLog() {
    Uri allMessages = Uri.parse("content://sms/");
     //Cursor cursor = managedQuery(allMessages, null, null, null, null); Both are same
    Cursor cursor = this.getContentResolver().query(allMessages, null,
            null, null, null);

    while (cursor.moveToNext()) {
        for (int i = 0; i < cursor.getColumnCount(); i++) {
            Log.d(cursor.getColumnName(i) + "", cursor.getString(i) + "");
        }
        Log.d("One row finished",
                "**************************************************");
    }

}


This is what I got from API 23:

public static final String COLUMN_ID = "_id";
public static final String COLUMN_THREAD_ID = "thread_id";
public static final String COLUMN_ADDRESS = "address";
public static final String COLUMN_PERSON = "person";
public static final String COLUMN_DATE = "date";
public static final String COLUMN_DATE_SENT = "date_sent";
public static final String COLUMN_PROTOCOL = "protocol";
public static final String COLUMN_READ = "read";
public static final String COLUMN_STATUS = "status";
public static final String COLUMN_TYPE = "type";
public static final String COLUMN_REPLY_PATH_PRESENT = "reply_path_present";
public static final String COLUMN_SUBJECT = "subject";
public static final String COLUMN_BODY = "body";
public static final String COLUMN_SERVICE_CENTER = "service_center";
public static final String COLUMN_LOCKED = "locked";
public static final String COLUMN_ERROR_CODE = "error_code";
public static final String COLUMN_SEEN = "seen";
public static final String COLUMN_TIMED = "timed";
public static final String COLUMN_DELETED = "deleted";
public static final String COLUMN_SYNC_STATE = "sync_state";
public static final String COLUMN_MARKER = "marker";
public static final String COLUMN_SOURCE = "source";
public static final String COLUMN_BIND_ID = "bind_id";
public static final String COLUMN_MX_STATUS = "mx_status";
public static final String COLUMN_MX_ID = "mx_id";
public static final String COLUMN_OUT_TIME = "out_time";
public static final String COLUMN_ACCOUNT = "account";
public static final String COLUMN_SIM_ID = "sim_id";
public static final String COLUMN_BLOCK_TYPE = "block_type";
public static final String COLUMN_ADVANCED_SEEN = "advanced_seen";
public static final String COLUMN_B2C_TTL = "b2c_ttl";
public static final String COLUMN_B2C_NUMBERS = "b2c_numbers";
public static final String COLUMN_FAKE_CELL_TYPE = "fake_cell_type";
public static final String COLUMN_URL_RISKY_TYPE = "url_risky_type";

And this is how I print all the contents:

    private void readAllMessages() {
    List<Sms> smssList = new ArrayList<Sms>();
    Sms sms;
    Cursor cursor = getContentResolver().query(Uri.parse("content://sms/inbox"), null, null, null, null);
    if (cursor.moveToFirst()) {
        String message = "";
        do {
            sms = new Sms();
            sms.set_id(cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_ID)));
            sms.setThreadId(cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_THREAD_ID)));
            sms.setAddress(cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_ADDRESS)));
            sms.setPerson((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_PERSON))));
            sms.setDate((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_DATE))));
            sms.setDateSent((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_DATE_SENT))));
            sms.setProtocol((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_PROTOCOL))));
            sms.setRead((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_READ))));
            sms.setStatus((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_STATUS))));
            sms.setType((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_TYPE))));
            sms.setReplyPathPresent((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_REPLY_PATH_PRESENT))));
            sms.setSubject((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_SUBJECT))));
            sms.setBody((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_BODY))));
            sms.setServiceCenter((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_SERVICE_CENTER))));
            sms.setLocked((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_LOCKED))));
            sms.setErrorCode((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_ERROR_CODE))));
            sms.setSeen((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_SEEN))));
            sms.setTimed((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_TIMED))));
            sms.setDeleted((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_DELETED))));
            sms.setSyncState((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_SYNC_STATE))));
            sms.setMarker((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_MARKER))));
            sms.setSource((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_SOURCE))));
            sms.setBindId((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_BIND_ID))));
            sms.setMxStatus((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_MX_STATUS))));
            sms.setMxId((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_MX_ID))));
            sms.setOutTime((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_OUT_TIME))));
            sms.setAccount((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_ACCOUNT))));
            sms.setSimId((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_SIM_ID))));
            sms.setBlockType((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_BLOCK_TYPE))));
            sms.setAdvancedSeen((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_ADVANCED_SEEN))));
            sms.setB2cTtl((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_B2C_TTL))));
            sms.setB2cNumbers((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_B2C_NUMBERS))));
            sms.setFakeCellType((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_FAKE_CELL_TYPE))));
            sms.setUrlRiskyType((cursor.getString(cursor.getColumnIndexOrThrow(Sms.COLUMN_URL_RISKY_TYPE))));

            Log.v(TAG, "SMS read " + sms);
            smssList.add(sms);
        } while (cursor.moveToNext());
    } else {
        Log.v(TAG, "The user does not have any sms");
    }
}

The source code could be found here: https://github.com/jiahaoliuliu/Akami/tree/feature/allSmsFields


Unfortunately the content provider for Sms and Mms (android.providers.Telephony) is not part of the public API at this moment. Until it is, you can define your own constants using this as a template.


You can take a look a the new API 19 : https://developer.android.com/reference/android/provider/Telephony.TextBasedSmsColumns.html https://developer.android.com/reference/android/provider/Telephony.Sms.html


Use the selectionArgs field

String limite = "the timestamp converted to String";
Cursor cur = c.getContentResolver().query(uriSMSURI, null,"date" + ">?", new String[] {limite},null);


public class main extends Activity {
    /** Called when the activity is first created. */
    String colName;
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);

        TextView tView = (TextView)findViewById(R.id.txtView);

        ContentResolver cr =getContentResolver();
        Uri uri = Uri.parse("content://sms/inbox");
        //Uri uri = Uri.parse("content://sms"); -- For all SMS
        //Uri uri = Uri.parse("content://sms/sent"); -- For all Sent Items
        //If you want to read the Sent SMS then change the URi to /sent.

        //In this example we are using Query as we have defined URi as above.
        //We have declared all the Column names we need in string array in the second parameter.
        //If you dont need all then leave null
        //Notice that we did not call managedQuery instead we used Query method of ContentResolver
        Cursor messagesCursor = cr.query(uri, new String[] { "_id","address","body","person"}, null,null, null);
        colName = "ColumnName" +"\n";
        colName = colName +  "--------------" + "\n";

        for(int loopCounter=0; loopCounter < messagesCursor.getColumnCount() ; loopCounter++)
        {
            colName = colName + messagesCursor.getColumnName(loopCounter) + "\n";

        }
        colName = colName +  "--------------" + "\n";

        if(messagesCursor.getCount() > 0)
        {
            while(messagesCursor.moveToNext())
            {
                colName = colName +  messagesCursor.getString(messagesCursor.getColumnIndex("body")) + "--";
                colName = colName +  messagesCursor.getString(messagesCursor.getColumnIndex("address")) + "\n";
            }
        }
        tView.setText(colName);


    }
}


Or you can do something like below:

for(String s : cursor.getColumnNames()){
     Log.d("smsColumns", "Column: " + s);
}
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜