数据插入外部sqlite数据库但未保存在android studio中 [英] data inserted into external sqlite database but not saving in android studio

查看:32
本文介绍了数据插入外部sqlite数据库但未保存在android studio中的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在使用外部 sqlite 数据库,而不是在我的 android studio 项目 中创建一个,因为该数据库将有一些已经填充的数据在其中.但我还必须插入更多数据.当我插入任何新数据时,它会显示新数据,但是当我关闭我的 android 应用程序并再次打开以查看数据时,通过应用程序新插入的数据以某种方式删除,只有预填充的数据显示.

I'm using an external sqlite database rather than creating one in my android studio project since the database will have some already populated data in it. But I have to insert some more data as well. And when I insert any new data, it shows the new data but as I close my android app and open again to see the data, the newly inserted data through the app are somehow deleted, only prepopulated data are shown.

我使用数据库浏览器来创建外部 sqlite 数据库并在那里预先填充一些数据.在我的 android studio 项目中,我将此数据库添加到我的资产文件夹中并实现了 SQLiteOpenHelper 类来访问此数据库.从数据库表中读取数据是成功的.现在,当我插入新数据时,我也可以临时读取新数据.暂时在我关闭我的应用程序后新数据丢失的意义上.

I am using DB browser for sqlite to create the external sqlite database and pre-populate it with some data there. In my android studio project, I added this database into my assets folder and implemented SQLiteOpenHelper class to access this database. Reading the data from the database table is a success. Now as I insert new data I can read the new data temporarily as well. Temporarily in the sense that after i close my app the new data are lost.

我的外部sqlite数据库表:

the table of my external sqlite database:

CREATE TABLE `table_name` (
`Id`    INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT,
`Content`   TEXT NOT NULL
);

SQLiteOpenHelper 类:

SQLiteOpenHelper class:

public class ProcessExternalDBHelper {
private static final String DATABASE_NAME = "database_name.db";
private static final int DATABASE_VERSION = 1;
private static String DATABASE_PATH = "";

private static final String DATABASE_TABLE = "table_name";
private static final String KEY_ROWID = "Id";
private static final String KEY_CONTENT = "Content";

private ExternalDbHelper ourHelper;
private final Context ourContext;
private SQLiteDatabase ourDatabase;

private static class ExternalDbHelper extends SQLiteOpenHelper {

    public ExternalDbHelper(Context context) {
        super(context, DATABASE_NAME, null, DATABASE_VERSION);
        if (Build.VERSION.SDK_INT >= 17) {
            DATABASE_PATH = context.getApplicationInfo().dataDir + 
"/databases/";
        } else {
            DATABASE_PATH = "/data/data/" + context.getPackageName() + 
"/databases/";
        }
    }

    @Override
    public void onCreate(SQLiteDatabase db) {

    }

    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int 
newVersion) {

    }
}

public ProcessExternalDBHelper(Context context) {
    ourContext = context;
}
//for reading
public ProcessExternalDBHelper openRead() throws SQLException {
    ourHelper = new ExternalDbHelper(ourContext);
    ourDatabase = ourHelper.getReadableDatabase();
    return this;
}
//for writing
public ProcessExternalDBHelper openWrite() throws SQLException{
    ourHelper = new ExternalDbHelper(ourContext);
    ourDatabase = ourHelper.getWritableDatabase();
    return this;
}

public void close() {
    if (ourHelper != null) {
        ourHelper.close();
    }
}

//Create database in activity
public void createDatabase() throws IOException {
    createDB();
}
//Create db if not exists
private void createDB() {
    boolean dbExists = checkDatabase();
    if (!dbExists) {
        openRead();             
        try {
            this.close();
            copyDatabase();
        } catch (IOException ie) {
            throw new Error("Error copying database");
        }
    }
}

private boolean checkDatabase() {
    boolean checkDB = false;
    try {
        String myPath = DATABASE_PATH + DATABASE_NAME;
        File dbfile = new File(myPath);
        checkDB = dbfile.exists();
    } catch (SQLiteException e) {

    }
    return checkDB;
}

private void copyDatabase() throws IOException {
    InputStream myInput = null;
    OutputStream myOutput = null;
    String outFileName = DATABASE_PATH + DATABASE_NAME;

    try {
        myInput = ourContext.getAssets().open(DATABASE_NAME);
        myOutput = new FileOutputStream(outFileName);

        byte[] buffer = new byte[1024];
        int length;
        while ((length = myInput.read(buffer)) > 0) {
            myOutput.write(buffer, 0, length);
        }
        myOutput.flush();
        myOutput.close();
        myInput.close();
    } catch (IOException ie) {
        throw new Error("Copydatabase() error");
    }
}
//To show all available contents in my database
public List<Model> findallContents() {
    List<Model> mContents = new ArrayList<>();

    String[] columns = new String[]{KEY_CONTENT};
    Cursor cursor = ourDatabase.query(DATABASE_TABLE, columns, null, null, 
null, null, null);
    int iContent = cursor.getColumnIndex(KEY_CONTENT);

    for (cursor.moveToFirst(); !cursor.isAfterLast(); cursor.moveToNext()) 
    {
        Model model= new Model();
        model.setContent(cursor.getString(iContent));

        mContents.add(model);
    }

    cursor.close();
    return mContents;
}

public void addContent(String content) {
    ContentValues contentValues = new ContentValues();
    contentValues.put(KEY_CONTENT, content);

    ourDatabase.insert(DATABASE_TABLE, null, contentValues);
    ourDatabase.close();
}

}

我的 Model.java 类:

My Model.java class:

public class Model {
    private String mContent;

    public String getContent() {
    return mContent;
    }

    public void setContent(String content) {
        this.mContent = content;
    }
}

最后是我读写数据的活动类:

Finally my activity class where i read and write the data:

public class MainActivity extends AppCompatActivity {

private EditText editText_Content;
private ImageButton imageButton_Save;
private List<Model> mContentsArrayList;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    ProcessExternalDBHelper myDbHelper = new ProcessExternalDBHelper(this);
    try {
        myDbHelper.createDatabase();
    } catch (IOException ioe) {
        throw new Error("Unable to CREATE DATABASE");
    } finally {
        myDbHelper.close();
    }

    initialize();

    GetContents();

    imageButton_Save.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            if (!(editText_Content.getText().toString().trim().isEmpty())) 
            {
                SaveContents();
            } 
        }
    });
}

private void initialize() {
    editText_Content = findViewById(R.id.editText_contents);
    imageButton_Save = findViewById(R.id.imageButton_save);

    mContentsArrayList = new ArrayList<>();
}
//GetContents and show them later in my RecyclerView
private void GetContents() {
    try {
        mContentsArrayList.clear();
        ProcessExternalDBHelper autoProcess = new 
    ProcessExternalDBHelper(this);
        autoProcess.openRead();
        mContentsArrayList.addAll(autoProcess.findallContents();
        autoProcess.close();
    } catch (Exception e) {

    }
}
//For saving content into database    
private void SaveContents() {
    String content = editText_Content.getText().toString();

    try {
        ProcessExternalDBHelper autoProcess = new 
ProcessExternalDBHelper(this);
        autoProcess.openWrite();   //for writing into database
        autoProcess.addContent(content);
        autoProcess.close();
        editText_Content.getText().clear();
    } catch (Exception e) {

    }
}

}

最后,我使用了 Sqlite(版本 3.10.1)、android studio(版本 3.0.1)、minSdkVersion 19 的 DB 浏览器.

Finally I am using DB Browser for Sqlite (ver 3.10.1), android studio (ver 3.0.1), minSdkVersion 19.

我希望新插入的数据被保存到数据库中,以后即使我关闭我的应用程序并稍后重新启动应用程序也能看到.谢谢!

I am expecting the newly inserted data into the database to be saved and later seen even when i close my app and and restart the app later. Thank You!

推荐答案

您的问题是 DATABASE_PATH 没有被重置,因此在调用 createDatabase 时为空.

Your issue is that DATABASE_PATH isn't being reset and is therefore empty when createDatabase is invoked.

所以检查数据库是否存在,找不到数据库(纯粹是在文件系统的最高层寻找database_db.db这个文件,这样这个文件就不会存在了) 并且数据库被复制,覆盖保存了数据的数据库.

Therefore the check to see if the database exists fails to find the database (it's looking purely for the file database_db.db at the highest level of the file system, as such the file will not exist) and the database is copied overwriting the database that has data saved into it.

我建议进行以下更改:-

I'd suggest the following changes :-

private boolean checkDatabase() {
    File dbfile = new File(ourContext.getDatabasePath(DATABASE_NAME).getPath());
    if ( dbfile.exists()) return true;
    File dbdir = dbfile.getParentFile();
    if (!dbdir.exists()) {
        dbdir.mkdirs();
    }
    return false;
}

  • 这样做的好处是,如果数据库目录不存在,则会创建该目录,并且它仅依赖于路径的数据库名称.
  • 也不需要 try/catch 结构.
  • 和可选的 :-

    private void copyDatabase() throws IOException {
        InputStream myInput = null;
        OutputStream myOutput = null;
        String outFileName = ourContext.getDatabasePath(DATABASE_NAME).getPath(); //<<<<<<<<<< CHANGED
    
        try {
            myInput = ourContext.getAssets().open(DATABASE_NAME);
            myOutput = new FileOutputStream(outFileName);
    
            byte[] buffer = new byte[1024];
            int length;
            while ((length = myInput.read(buffer)) > 0) {
                myOutput.write(buffer, 0, length);
            }
            myOutput.flush();
            myOutput.close();
            myInput.close();
        } catch (IOException ie) {
            throw new Error("Copydatabase() error");
        }
    }
    

    • 请注意,如果应用了上述内容,则无需检查 SDK 版本,因为 getDatabasePath 方法会获取正确的路径.
    • 这篇关于数据插入外部sqlite数据库但未保存在android studio中的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆