在Content provider实现中使用SQLiteOpenHelper

在前面的编写最简单的Content Provider的示例是很粗糙的,目的是让读者尽快了解怎样编写和使用Content provider。

其中一个事情是,如果重复启动该应用,会多次插入,产生重复的记录并显示到activity中。在上个例子中没有做处理,比如判断是否存在数据库等等。

Android为SQLite提供了便利的API,方便自动创建新的数据库或者升级数据库。其实本文的示例并不一定要在Content provider使用情况下,是在android sqlite编程下都可以用的。

android提供了这个类:

android.database.sqlite.SQLiteOpenHelper

有两个抽象方法需要继承以后实现:

public void onCreate(SQLiteDatabase database)

public void onUpgrade(SQLiteDatabase database, int oldVersion,
                int newVersion)

其中第一个onCreate方法,在实现代码中要写出怎样创建你需要的数据库和表,以及一些初始数据。这实际上是个回调(callback),android会自动判断是否有该数据库,如果没有,就调用这个方法创建。

onUpgrade方法,在这种情况下调用,你的应用中的sqlite数据库升级了,比如,表结构都发生了变化,那么android就会调用这个方法升级数据库。你需要实现这个方法,指出如何升级数据库,在下面示例中,是很简单的一种做法,就是删除就版本数据库,重新创建新版本的数据库。复杂的做法(也是平滑升级的做法)是,把旧数据库中的信息导入到新数据库中。

程序依据编写最简单的Content Provider做了改动,只改动了MyContentProvider的代码:

package com.easymorse.cp;

import android.content.ContentProvider;
import android.content.ContentValues;
import android.content.Context;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.database.sqlite.SQLiteStatement;
import android.database.sqlite.SQLiteDatabase.CursorFactory;
import android.net.Uri;
import android.util.Log;

public class MyContentProvider extends ContentProvider {

    public static final Uri CONTENT_URI = Uri
            .parse("content://com.easymorse.cp.mycp");

    public static final String _ID = "id";

    public static final String NAME = "name";

    public static final String DYNASTY = "dynasty";

    public static final String START_YEAR = "start_year";

    private static SQLiteDatabase database;

    private static final int DATABASE_VERSION = 1;

    @Override
    public int delete(Uri uri, String selection, String[] selectionArgs) {
        return 0;
    }

    @Override
    public String getType(Uri uri) {
        return null;
    }

    @Override
    public Uri insert(Uri uri, ContentValues contentValues) {
        // TODO Auto-generated method stub
        return null;
    }

    @Override
    public boolean onCreate() {
        database = new MyDatabaseHelper(getContext(), "emperors", null,
                DATABASE_VERSION).getWritableDatabase();
        return database != null;
    }

    @Override
    public Cursor query(Uri uri, String[] projection, String selection,
            String[] selectionArgs, String sortOrder) {
        Cursor cursor = database.rawQuery("select * from emperors", null);
        return cursor;
    }

    @Override
    public int update(Uri uri, ContentValues contentValues, String selection,
            String[] selectionArgs) {
        // TODO Auto-generated method stub
        return 0;
    }

    private static class MyDatabaseHelper extends SQLiteOpenHelper {

        public MyDatabaseHelper(Context context, String name,
                CursorFactory factory, int version) {
            super(context, name, factory, version);
        }

        @Override
        public void onCreate(SQLiteDatabase database) {
            database.execSQL("create table if not exists emperors("
                    + " id integer primary key autoincrement," + " name text,"
                    + "dynasty text," + "start_year text" + ");");

            SQLiteStatement statement = database
                    .compileStatement("insert into emperors(name,dynasty,start_year) values(?,?,?)");
            int index = 1;
            statement.bindString(index++, "朱元璋");
            statement.bindString(index++, "明");
            statement.bindString(index++, "1398");
            statement.execute();

            index = 1;
            statement.bindString(index++, "玄烨");
            statement.bindString(index++, "清");
            statement.bindString(index++, "1722");
            statement.execute();

            statement.close();
        }

        @Override
        public void onUpgrade(SQLiteDatabase database, int oldVersion,
                int newVersion) {
            Log.w("mycp", "updating database from version " + oldVersion
                    + " to " + newVersion);
            database.execSQL("drop table if exists emperors");
            onCreate(database);
        }

    }

}

 

上面提到的bug就解决了。

完整源代码见:

http://easymorse.googlecode.com/svn/tags/content.provider-0.2.0/

PDF下載    发送文章为PDF   

这篇文章上的评论的 RSS feed TrackBack URI

Leave a Reply