/* * Copyright (C) 2012 www.amsoft.cn * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.ab.db.orm; import java.io.File; import android.content.Context; import android.database.sqlite.SQLiteDatabase; import android.database.sqlite.SQLiteDatabase.CursorFactory; import android.database.sqlite.SQLiteException; import android.database.sqlite.SQLiteOpenHelper; // TODO: Auto-generated Javadoc /** * © 2012 amsoft.cn * 名称:AbSDSQLiteOpenHelper.java * 描述:SD卡中保存数据库 * * @author 还如一梦中 * @version v1.0 * @date:2013-7-23 上午9:47:10 */ public abstract class AbSDSQLiteOpenHelper extends SQLiteOpenHelper{ /** 应用Context. */ private final Context mContext; /** 数据库名. */ private final String mName; /** 数据库文件保存文件夹全路径. */ private final String mDir; /** 数据库查询的游标工厂. */ private final SQLiteDatabase.CursorFactory mFactory; /** 数据库的新版本号. */ private final int mNewVersion; /** 数据库对象. */ private SQLiteDatabase mDatabase = null; /** 是否已经初始化过. */ private boolean mIsInitializing = false; /** * 初始化一个AbSDSQLiteOpenHelper对象. * * @param context 应用Context * @param path 要放到SDCard下的文件夹路径 * @param name 数据库名 * @param factory 数据库查询的游标工厂 * @param version 数据库的新版本号 */ public AbSDSQLiteOpenHelper(Context context,String dir,String name, CursorFactory factory, int version) { super(context, name, factory, version); if (version < 1) throw new IllegalArgumentException("Version must be >= 1, was " + version); mContext = context; mDir = dir; mName = name; mFactory = factory; mNewVersion = version; } /** * 获取可写权限的数据库对象. * * @return 数据库对象 */ public synchronized SQLiteDatabase getWritableDatabase() { if (mDatabase != null && mDatabase.isOpen() && !mDatabase.isReadOnly()) { //已经获取过 return mDatabase; } if (mIsInitializing) { throw new IllegalStateException("数据库已被占用getWritableDatabase()"); } boolean success = false; SQLiteDatabase db = null; try { mIsInitializing = true; if (mName == null) { //创建一个内存支持SQLite数据库 db = SQLiteDatabase.create(null); } else { //创建一个文件支持SQLite数据库 String path = mDir + File.separator + mName; db = SQLiteDatabase.openOrCreateDatabase(path,mFactory); } int version = db.getVersion(); if (version != mNewVersion) { db.beginTransaction(); try { if (version == 0) { onCreate(db); } else { onUpgrade(db, version, mNewVersion); } db.setVersion(mNewVersion); db.setTransactionSuccessful(); } finally { db.endTransaction(); } } onOpen(db); success = true; return db; } finally { //释放占有 mIsInitializing = false; if (success) { if (mDatabase != null) { try { mDatabase.close(); } catch (Exception e) { } } mDatabase = db; } else { if (db != null) db.close(); } } } /** * 获取可读权限的数据库对象.. * * @return 数据库对象 */ public synchronized SQLiteDatabase getReadableDatabase() { if (mDatabase != null && mDatabase.isOpen()) { //已经获取过 return mDatabase; } if (mIsInitializing) { throw new IllegalStateException("数据库已被占用getReadableDatabase()"); } //都是写获取写的数据库 SQLiteDatabase db = null; try { db = getWritableDatabase(); mDatabase = db; } catch (Exception e1) { try { mIsInitializing = true; String path = mDir + File.separator + mName; db = SQLiteDatabase.openDatabase(path, mFactory, SQLiteDatabase.OPEN_READONLY); if (db.getVersion() != mNewVersion) { throw new SQLiteException("不能更新只读数据库的版本 from version " + db.getVersion() + " to " + mNewVersion + ": " + path); } onOpen(db); mDatabase = db; return mDatabase; }catch (SQLiteException e) { } finally { mIsInitializing = false; if (db != null && db != mDatabase) db.close(); } } return mDatabase; } /** * 数据库被打开. * * @param db 被打开的数据库 */ public void onOpen(SQLiteDatabase db) {} /** * 数据库被关闭. * */ public synchronized void close() { if (mIsInitializing) throw new IllegalStateException("Closed during initialization"); if (mDatabase != null && mDatabase.isOpen()) { mDatabase.close(); mDatabase = null; } } /** * 数据库被创建事件. * * @param db 被创建的数据库 */ public abstract void onCreate(SQLiteDatabase db); /** * 数据库被重建. * * @param db 被创建的数据库 * @param oldVersion 原来的数据库版本 * @param newVersion 新的数据库版本 */ public abstract void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion); }