package org.orange.familylink.database;
import java.util.Date;
import org.orange.familylink.data.Contact;
import org.orange.familylink.data.Message;
import org.orange.familylink.data.Message.Code;
import org.orange.familylink.data.MessageLogRecord.Status;
import org.orange.familylink.sms.SmsMessage;
import android.content.ContentUris;
import android.content.ContentValues;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.net.Uri;
import android.test.ProviderTestCase2;
import android.test.mock.MockContentResolver;
public class MessagesProviderTest extends ProviderTestCase2<MessagesProvider> {
//测试无效的uri
private static final Uri INVALID_URI = Uri.withAppendedPath(Contract.Messages.MESSAGES_URI, "invalid");
//provider测试中的帮助类
private MockContentResolver mMockResolver;
//用于获取数据库
private SQLiteDatabase db;
//测试联系人时用的一些记录
private final MessageInfo[] TEST_MESSAGES = {
new MessageInfo("12345678900"),
new MessageInfo("12345678900"),
new MessageInfo("222-7135"),
new MessageInfo("222-7135"),
new MessageInfo("10086"),
new MessageInfo("10086"),
new MessageInfo("10000"),
new MessageInfo("10000")
};
//匹配全部的mime
private final static String MIME_TYPES_ALL = "*/*";
//测试不存在的mime
private final static String MIME_TYPES_NONE = "qwer/qwer";
//测试单项的mime
private final static String MIME_TYPE_ITEM = "vnd.android.cursor.item/vnd.familylink.messages";
/**
* 构造方法告诉测试类要测试的父类和权威路径
*/
public MessagesProviderTest() {
super(MessagesProvider.class, Contract.Messages.AUTHORITY);
}
/**
* 在这个方法中初始化帮助类和数据库的操作
*/
@Override
protected void setUp() throws Exception{
super.setUp();
mMockResolver = getMockContentResolver();
db = getProvider().getOpenHelperForTest().getWritableDatabase();
}
/**
* 结束时调用
*/
@Override
protected void tearDown() throws Exception {
super.tearDown();
}
/**
* 这是个私有的方法内部调用,在测试类中只有为public且为无参数的方法才会被测试调用
*/
private void insertData(){
for(int i = 0; i < TEST_MESSAGES.length; i++){
Contact mContact = new Contact();
mContact.setId((long)i);
Message mMessage = new SmsMessage();
mMessage.setBody("here" + i);
mMessage.setCode(Code.EXTRA_BITS);
TEST_MESSAGES[i].setContactId(mContact);
TEST_MESSAGES[i].setTime(new Date(2013/8/5));
TEST_MESSAGES[i].setStatus(Status.DELIVERED);
TEST_MESSAGES[i].setBody(mMessage);
TEST_MESSAGES[i].setCode(mMessage);
db.insertOrThrow(Contract.DATABASE_MESSAGES_TABLE, null, TEST_MESSAGES[i].getContentValues());
}
}
/**
* 对uri和getType方法测试
*/
public void testUriAndGetType(){
String mimeType = mMockResolver.getType(Contract.Messages.MESSAGES_URI);
assertEquals(Contract.Messages.MESSAGES_TYPE, mimeType);
Uri messageIdUri = ContentUris.withAppendedId(Contract.Messages.MESSAGES_ID_URI, 1);
mimeType = mMockResolver.getType(messageIdUri);
assertEquals(Contract.Messages.MESSAGES_ITEM_TYPE, mimeType);
mimeType = mMockResolver.getType(INVALID_URI);
}
/**
* 对uri流类型操作
*/
public void testGetStreamTypes(){
assertNull(mMockResolver.getStreamTypes(Contract.Messages.MESSAGES_URI, MIME_TYPES_ALL));
Uri testUri = Uri.withAppendedPath(Contract.Messages.MESSAGES_ID_URI, "1");
String mimeType[] = mMockResolver.getStreamTypes(testUri, MIME_TYPES_ALL);
assertNull(mimeType);
mimeType = mMockResolver.getStreamTypes(testUri, MIME_TYPES_NONE);
assertNull(mimeType);
}
/**
* 测试查询,这里的查询用的Uri是集合类型的
*/
public void testQueriesOnMessagesUri() {
//测试的字段
final String[] TEST_PROJECTION = {
Contract.Messages.COLUMN_NAME_CONTACT_ID,
Contract.Messages.COLUMN_NAME_ADDRESS,
Contract.Messages.COLUMN_NAME_TIME,
Contract.Messages.COLUMN_NAME_STATUS,
Contract.Messages.COLUMN_NAME_BODY,
Contract.Messages.COLUMN_NAME_CODE
};
//测试的where条件
final String TITLE_SELECTION = Contract.Messages.COLUMN_NAME_ADDRESS + " = " + "?";
final String SELECTION_COLUMNS =
TITLE_SELECTION + " OR " + TITLE_SELECTION + " OR " + TITLE_SELECTION;
final String[] SELECTION_ARGS = { "12345678900", "10086", "10000" };
//sort
final String SORT_ORDER = Contract.Messages.COLUMN_NAME_TIME + " ASC";
//查询contacts的集合型uri也就是查询contacts表
Cursor cursor = mMockResolver.query(
Contract.Messages.MESSAGES_URI,
null,
null,
null,
null
);
//此时查询结果肯定为空
assertEquals(0, cursor.getCount());
//现在对message表插入数据
insertData();
//进行再次的查询
cursor = mMockResolver.query(
Contract.Messages.MESSAGES_URI,
null,
null,
null,
null
);
//这是查询结果的个数就为测试输入的用例的个数
assertEquals(TEST_MESSAGES.length, cursor.getCount());
//查询中加入‘project’就是查询时选着要查询的字段
Cursor projectionCursor = mMockResolver.query(
Contract.Messages.MESSAGES_URI,
TEST_PROJECTION,
null,
null,
null
);
//判断查询结果的字段个数是否真确
assertEquals(TEST_PROJECTION.length, projectionCursor.getColumnCount());
//对查询结果的字段名检查
assertEquals(TEST_PROJECTION[0], projectionCursor.getColumnName(0));
assertEquals(TEST_PROJECTION[1], projectionCursor.getColumnName(1));
//综合的查询
projectionCursor = mMockResolver.query(
Contract.Messages.MESSAGES_URI,
TEST_PROJECTION,
SELECTION_COLUMNS,
SELECTION_ARGS,
SORT_ORDER
);
//此时的查询结果应为where条件给出所进行查询的结果的个数
assertEquals(SELECTION_ARGS.length*2, projectionCursor.getCount());
int index = 0;
while (projectionCursor.moveToNext()) {
assertEquals(SELECTION_ARGS[index], projectionCursor.getString(1));
index++;
projectionCursor.moveToNext();
}
assertEquals(SELECTION_ARGS.length, index);
}
/**
* 测试查询,这里查询用的uri是单项记录类型
*/
public void testQueriesOnMessageIdUri() {
final String SELECTION_COLUMNS = Contract.Messages.COLUMN_NAME_ADDRESS + " = " + "?";
final String[] SELECTION_ARGS = { "10086" };
final String SORT_ORDER = Contract.Messages.COLUMN_NAME_TIME + " ASC";
final String[] MESSAGE_ID_PROJECTION = {
Contract.Messages._ID,
Contract.Messages.COLUMN_NAME_CONTACT_ID,
Contract.Messages.COLUMN_NAME_TIME,
Contract.Messages.COLUMN_NAME_STATUS,
Contract.Messages.COLUMN_NAME_BODY,
Contract.Messages.COLUMN_NAME_CODE};
Uri messageIdUri = ContentUris.withAppendedId(Contract.Messages.MESSAGES_ID_URI, 1);
Cursor cursor = mMockResolver.query(
messageIdUri,
null,
null,
null,
null
);
assertEquals(0,cursor.getCount());
insertData();
cursor = mMockResolver.query(
Contract.Messages.MESSAGES_URI,
MESSAGE_ID_PROJECTION,
SELECTION_COLUMNS,
SELECTION_ARGS,
SORT_ORDER
);
assertEquals(2, cursor.getCount());
assertTrue(cursor.moveToFirst());
int inputMessageId = cursor.getInt(0);
messageIdUri = ContentUris.withAppendedId(Contract.Messages.MESSAGES_ID_URI, inputMessageId);
cursor = mMockResolver.query(messageIdUri,
MESSAGE_ID_PROJECTION,
SELECTION_COLUMNS,
SELECTION_ARGS,
SORT_ORDER
);
assertEquals(1, cursor.getCount());
assertTrue(cursor.moveToFirst());
assertEquals(inputMessageId, cursor.getInt(0));
}
public void testInserts() {
MessageInfo message = new MessageInfo("10086");
Contact mContact = new Contact();
mContact.setId((long)10);
Message mMessage = new SmsMessage();
mMessage.setBody("here" + "10");
mMessage.setCode(Code.EXTRA_BITS);
message.setContactId(mContact);
message.setTime(new Date(2013/8/5));
message.setStatus(Status.DELIVERED);
message.setBody(mMessage);
message.setCode(mMessage);
Uri rowUri = mMockResolver.insert(
Contract.Messages.MESSAGES_URI,
message.getContentValues()
);
long messageId = ContentUris.parseId(rowUri);
Cursor cursor = mMockResolver.query(
Contract.Messages.MESSAGES_URI,
null,
null,
null,
null
);
assertEquals(1, cursor.getCount());
assertTrue(cursor.moveToFirst());
int addressIndex = cursor.getColumnIndex(Contract.Messages.COLUMN_NAME_ADDRESS);
int contactIdIndex = cursor.getColumnIndex(Contract.Messages.COLUMN_NAME_CONTACT_ID);
int timeIndex = cursor.getColumnIndex(Contract.Messages.COLUMN_NAME_TIME);
int directionIndex = cursor.getColumnIndex(Contract.Messages.COLUMN_NAME_STATUS);
int bodyIndex = cursor.getColumnIndex(Contract.Messages.COLUMN_NAME_BODY);
int codeIndex = cursor.getColumnIndex(Contract.Messages.COLUMN_NAME_CODE);
assertEquals(message.address, cursor.getString(addressIndex));
assertEquals(message.contactId, cursor.getLong(contactIdIndex));
assertEquals(message.time, cursor.getLong(timeIndex));
assertEquals(String.valueOf(message.status), cursor.getString(directionIndex));
assertEquals(message.body, cursor.getString(bodyIndex));
assertEquals(message.code, cursor.getInt(codeIndex));
ContentValues values = message.getContentValues();
values.put(Contract.Messages._ID, (int) messageId);
try {
rowUri = mMockResolver.insert(Contract.Messages.MESSAGES_URI, values);
fail("Expected insert failure for existing record but insert succeeded.");
} catch (Exception e) {
}
}
/**
* 测试删除操作
*/
public void testDeletes() {
//where条件
final String SELECTION_COLUMNS = Contract.Messages.COLUMN_NAME_ADDRESS + " = " + "?";
final String[] SELECTION_ARGS = { "10086" };
//进行删除
int rowsDeleted = mMockResolver.delete(
Contract.Messages.MESSAGES_URI,
SELECTION_COLUMNS,
SELECTION_ARGS
);
//此时是没有删除任何的行,前面的插入对这个函数没影响
assertEquals(0, rowsDeleted);
//插入测试的用例
insertData();
//删除
rowsDeleted = mMockResolver.delete(
Contract.Messages.MESSAGES_URI,
SELECTION_COLUMNS,
SELECTION_ARGS
);
//此时是删除了一行
assertEquals(2, rowsDeleted);
//查询一下看是否真被删除
Cursor cursor = mMockResolver.query(
Contract.Messages.MESSAGES_URI,
null,
SELECTION_COLUMNS,
SELECTION_ARGS,
null
);
//这里可得知真的被删除
assertEquals(0, cursor.getCount());
}
/**
* 测试更新操作
*/
public void testUpdates() {
final String SELECTION_COLUMNS = Contract.Messages.COLUMN_NAME_ADDRESS + " = " + "?";
final String[] selectionArgs = { "10000" };
ContentValues values = new ContentValues();
values.put(Contract.Messages.COLUMN_NAME_STATUS, Status.SENT.name());
int rowsUpdated = mMockResolver.update(
Contract.Messages.MESSAGES_URI,
values,
SELECTION_COLUMNS,
selectionArgs
);
assertEquals(0, rowsUpdated);
insertData();
rowsUpdated = mMockResolver.update(
Contract.Messages.MESSAGES_URI,
values,
SELECTION_COLUMNS,
selectionArgs
);
assertEquals(2, rowsUpdated);
}
/**
* 内部类用来生成测试用例的
* @author orange team
*
*/
private static class MessageInfo{
long contactId;
String address;
long time;
String status;
String body;
int code;
public MessageInfo(String mAddress){
address = mAddress;
}
void setContactId(Contact mContact){
contactId = mContact.getId();
}
void setTime(Date mDate){
time = mDate.getTime();
}
void setStatus(Status mStatus){
status = mStatus.name();
}
void setBody(Message mMessage){
body = mMessage.getBody();
}
void setCode(Message mMessage){
code = mMessage.getCode();
}
public ContentValues getContentValues(){
ContentValues v = new ContentValues();
v.put(Contract.Messages.COLUMN_NAME_CONTACT_ID, contactId);
v.put(Contract.Messages.COLUMN_NAME_ADDRESS, address);
v.put(Contract.Messages.COLUMN_NAME_TIME, time);
v.put(Contract.Messages.COLUMN_NAME_STATUS, status);
v.put(Contract.Messages.COLUMN_NAME_BODY, body);
v.put(Contract.Messages.COLUMN_NAME_CODE, code);
return v;
}
}
}