@Override
 public Uri insert(Uri uri, ContentValues values) {
   final String table = getTableNameForContentUri(uri);
   if (table == null) return null;
   if (TABLE_DIRECT_MESSAGES_CONVERSATION.equals(table))
     // read-only here.
     return null;
   else if (TABLE_DIRECT_MESSAGES.equals(table)) // read-only here.
   return null;
   else if (TABLE_DIRECT_MESSAGES_CONVERSATIONS_ENTRY.equals(table)) // read-only
     // here.
     return null;
   final long row_id = database.insert(table, null, values);
   onDatabaseUpdated(uri, true);
   try {
     return Uri.withAppendedPath(uri, String.valueOf(row_id));
   } catch (final SQLiteException e) {
     mErrorToastHandler.sendMessage(mErrorToastHandler.obtainMessage(0, e));
   }
   return null;
 }
 @Override
 public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) {
   final String table = getTableNameForContentUri(uri);
   int result = 0;
   if (table != null) {
     if (TABLE_DIRECT_MESSAGES_CONVERSATION.equals(table))
       // read-only here.
       return 0;
     else if (TABLE_DIRECT_MESSAGES.equals(table)) // read-only here.
     return 0;
     else if (TABLE_DIRECT_MESSAGES_CONVERSATIONS_ENTRY.equals(table)) // read-only
       // here.
       return 0;
     try {
       result = database.update(table, values, selection, selectionArgs);
     } catch (final SQLiteException e) {
       mErrorToastHandler.sendMessage(mErrorToastHandler.obtainMessage(0, e));
     }
   }
   if (result > 0) {
     onDatabaseUpdated(uri, false);
   }
   return result;
 }
 @Override
 public Cursor query(
     Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder) {
   final String table = getTableNameForContentUri(uri);
   if (table == null) return null;
   final String projection_string =
       projection != null ? ArrayUtils.buildString(projection, ',', false) : "*";
   if (TABLE_DIRECT_MESSAGES_CONVERSATION.equals(table)) {
     // read-only here.
     final List<String> segments = uri.getPathSegments();
     if (segments.size() != 3) return null;
     final StringBuilder sql_builder = new StringBuilder();
     sql_builder.append("SELECT " + projection_string);
     sql_builder.append(" FROM " + TABLE_DIRECT_MESSAGES_INBOX);
     sql_builder.append(" WHERE " + DirectMessages.ACCOUNT_ID + " = " + segments.get(1));
     sql_builder.append(" AND " + DirectMessages.SENDER_ID + " = " + segments.get(2));
     if (selection != null) {
       sql_builder.append(" AND " + selection);
     }
     sql_builder.append(" UNION ");
     sql_builder.append("SELECT " + projection_string);
     sql_builder.append(" FROM " + TABLE_DIRECT_MESSAGES_OUTBOX);
     sql_builder.append(" WHERE " + DirectMessages.ACCOUNT_ID + " = " + segments.get(1));
     sql_builder.append(" AND " + DirectMessages.RECIPIENT_ID + " = " + segments.get(2));
     if (selection != null) {
       sql_builder.append(" AND " + selection);
     }
     sql_builder.append(
         " ORDER BY "
             + (sortOrder != null ? sortOrder : DirectMessages.Conversation.DEFAULT_SORT_ORDER));
     try {
       return database.rawQuery(sql_builder.toString(), selectionArgs);
     } catch (final SQLiteException e) {
       mErrorToastHandler.sendMessage(mErrorToastHandler.obtainMessage(0, e));
     }
   } else if (TABLE_DIRECT_MESSAGES_CONVERSATION_SCREEN_NAME.equals(table)) {
     // read-only here.
     final List<String> segments = uri.getPathSegments();
     if (segments.size() != 3) return null;
     final StringBuilder sql_builder = new StringBuilder();
     sql_builder.append("SELECT " + projection_string);
     sql_builder.append(" FROM " + TABLE_DIRECT_MESSAGES_INBOX);
     sql_builder.append(" WHERE " + DirectMessages.ACCOUNT_ID + " = " + segments.get(1));
     sql_builder.append(
         " AND " + DirectMessages.SENDER_SCREEN_NAME + " = '" + segments.get(2) + "'");
     if (selection != null) {
       sql_builder.append(" AND " + selection);
     }
     sql_builder.append(" UNION ");
     sql_builder.append("SELECT " + projection_string);
     sql_builder.append(" FROM " + TABLE_DIRECT_MESSAGES_OUTBOX);
     sql_builder.append(" WHERE " + DirectMessages.ACCOUNT_ID + " = " + segments.get(1));
     sql_builder.append(
         " AND " + DirectMessages.RECIPIENT_SCREEN_NAME + " = '" + segments.get(2) + "'");
     if (selection != null) {
       sql_builder.append(" AND " + selection);
     }
     sql_builder.append(
         " ORDER BY "
             + (sortOrder != null ? sortOrder : DirectMessages.Conversation.DEFAULT_SORT_ORDER));
     try {
       return database.rawQuery(sql_builder.toString(), selectionArgs);
     } catch (final SQLiteException e) {
       mErrorToastHandler.sendMessage(mErrorToastHandler.obtainMessage(0, e));
     }
   } else if (TABLE_DIRECT_MESSAGES.equals(table)) {
     // read-only here.
     final StringBuilder sql_builder = new StringBuilder();
     sql_builder.append("SELECT " + projection_string);
     sql_builder.append(" FROM " + TABLE_DIRECT_MESSAGES_INBOX);
     if (selection != null) {
       sql_builder.append(" WHERE " + selection);
     }
     sql_builder.append(" UNION ");
     sql_builder.append("SELECT " + projection_string);
     sql_builder.append(" FROM " + TABLE_DIRECT_MESSAGES_OUTBOX);
     if (selection != null) {
       sql_builder.append(" WHERE " + selection);
     }
     sql_builder.append(
         " ORDER BY " + (sortOrder != null ? sortOrder : DirectMessages.DEFAULT_SORT_ORDER));
     try {
       return database.rawQuery(sql_builder.toString(), selectionArgs);
     } catch (final SQLiteException e) {
       mErrorToastHandler.sendMessage(mErrorToastHandler.obtainMessage(0, e));
     }
   } else if (TABLE_DIRECT_MESSAGES_CONVERSATIONS_ENTRY.equals(table)) {
     try {
       return database.rawQuery(
           DirectMessages.ConversationsEntry.buildSQL(parseInt(uri.getLastPathSegment())), null);
     } catch (final SQLiteException e) {
       mErrorToastHandler.sendMessage(mErrorToastHandler.obtainMessage(0, e));
     }
   } else {
     try {
       return database.query(table, projection, selection, selectionArgs, null, null, sortOrder);
     } catch (final SQLiteException e) {
       mErrorToastHandler.sendMessage(mErrorToastHandler.obtainMessage(0, e));
     }
   }
   return null;
 }