Search…

Lưu Trữ Dữ Liệu với SQLite trong Android

15/11/20205 min read
Giới thiệu cách lưu trữ dữ liệu, truy cập, thêm xóa và chỉnh sửa thông tin với SQLite.

SQLite là 1 loại cơ sở dữ liệu có quy mô nhỏ, đơn giản, không cần cài đặt, không cần cấu hình, và không cần cài driver cho SQLite, được tích hợp sẵn trong Android từ API 1 và kết nối thông qua JDBC.

Trang chủ SQLite: https://www.sqlite.org/

Thao tác với SQLite trong Android

Thao tác cơ bản với SQLite trong Android gồm:

  • Create database
  • Create table
  • Select data
  • Insert data
  • Update data
  • Delete data

Ví dụ database tên là DICTIONARY_DB với 1 bảng là WORD có các trường như dưới đây:

Column Kiểu dữ liệu Ghi chú
id INTEGER Id của word, khoá chính, giá trị tự động tăng
word TEXT Từ
mean TEXT Nghĩa của từ

Tạo model tên Word.java ứng với bảng Word như sau:

public class Word {
    private int mId;
    private String mWord;
    private String mMean;

    public Word() {
      // TODO something
    }

    public Word(int id, String word, String mean) {
        this.mId = id;
        this.mWord = word;
        this.mMean = mean;
    }

    public Word(String word, String mean) {
        this.mWord = word;
        this.mMean = mean;
    }

    public void setMean(String mean) {
        this.mMean = mean;
    }

    public void setWord(String word) {
        this.mWord = word;
    }

    public int getId() {
        return mId;
    }

    public String getWord() {
        return mWord;
    }

    public String getMean() {
        return mMean;
    }
}

Để sử dụng SQLite trong Android phải tạo lớp kế thừa từ lớp SQLiteDatabaseHelper implement 2 phương thức onCreate() và phương thức onUpgrade()

public class DatabaseHelper extends SQLiteOpenHelper

Phương thức onCreate()

@Override
public void onCreate(SQLiteDatabase db) {
    // Thực thi các câu lệnh tạo bảng
    // Sử dụng db.execSQL(sql); chạy câu lênh sql tạo bảng
}

Phương thức onUpgrade()

@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
    // Gọi khi thay đổi DATABASE_VERSION
    // Thường sử dụng để thay đổi cấu trúc bảng (ALTER, DROP, ADD CONSTRAIN...)
}

Constructor

private DatabaseHelper(Context context) {
    super(context, DATABASE_NAME, null, DATABASE_VERSION);
    Log.e(TAG, "DatabaseHelper: ");
}

Phạm vi constructor là private, vì database có thể truy cập được bất cứ đâu trong ứng dụng (Activity, Fragment, Service, ...). Sử dụng singleton pattern nhằm đảm bảo trong ứng dụng có duy nhất 1 đối tượng DatabaseHelper để quản lý việc thao tác trên SQLite.

public static DatabaseHelper getInstance(Context context) {
    if (sInstance == null)
        sInstance = new DatabaseHelper(context.getApplicationContext());
    return sInstance;
}

public class DatabaseHelper extends SQLiteOpenHelper {
    private static final String TAG = "DatabaseHelper";
    private static final String DATABASE_NAME = "DICTIONARY_DB";
    private static final int DATABASE_VERSION = 1;
    private static final String TABLE_WORD = "WORD";
    private static final String ID_COLUMN = "id";
    private static final String WORD_COLUMN = "word";
    private static final String MEAN_COLUMN = "mean";

    private static final String CREATE_WORD_TABLE_SQL =
        "CREATE TABLE " + TABLE_WORD + " (" +
            ID_COLUMN + " INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT," +
            WORD_COLUMN + " TEXT NOT NULL," +
            MEAN_COLUMN + " TEXT NOT NULL" +
        ")";

    private static DatabaseHelper sInstance;
    public static DatabaseHelper getInstance(Context context) {
        if (sInstance == null)
            sInstance = new DatabaseHelper(context.getApplicationContext());
        return sInstance;
    }

    private DatabaseHelper(Context context) {
        super(context, DATABASE_NAME, null, DATABASE_VERSION);
        Log.e(TAG, "DatabaseHelper: ");
    }

    @Override
    public void onCreate(SQLiteDatabase db) {
        Log.e(TAG, "onCreate: ");
        db.execSQL(CREATE_WORD_TABLE_SQL);
    }

    @Override
    public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
        Log.e(TAG, "onUpgrade: ");
        db.execSQL("DROP TABLE IF EXISTS " + TABLE_WORD);
        onCreate(db);
    }
}

Insert data

public boolean insertWord(Word word) {
    SQLiteDatabase db = getWritableDatabase();
    ContentValues values = new ContentValues();
    values.put(WORD_COLUMN, word.getWord());
    values.put(MEAN_COLUMN, word.getMean());
    long rowId = db.insert(TABLE_WORD, null, values);
    db.close();

    return rowId != -1;
}

Sử dụng đối tượng ContentValues để đặt các giá trị ứng với tên cột và sử dụng phương thức insertWord() của SQLiteDatabase để tiến hành ghi xuống database. Phương thức sẽ trả về true nếu chèn dữ liệu thành công, ngược lại trả về false.

Select data

Đối với việc lấy data từ SQLite, có 2 phương thức là query() và rawQuery(), 2 phương thức này trả về đối tượng cursor, đối tượng này có thể lấy dữ liệu của từng dòng.

Lấy từ theo id:

public Word getWord(int id) {
    SQLiteDatabase db = getReadableDatabase();
    Word word = null;
    Cursor cursor = db.query(TABLE_WORD, new String[]{ ID_COLUMN, WORD_COLUMN, MEAN_COLUMN }, ID_COLUMN + " = ?",
                            new String[]{String.valueOf(id)}, null, null, null);
    if (cursor != null && cursor.moveToFirst()) {
        word = new Word(cursor.getInt(0), cursor.getString(1), cursor.getString(2));
        cursor.close();
    }
    db.close();
    return word;
}

Lấy tất cả các từ có trong database:

public List<Word> getAllWord() {
    SQLiteDatabase db = getReadableDatabase();
    List<Word> words = new ArrayList<>();
    String sql = "SELECT * FROM " + TABLE_WORD;
    Cursor cursor = db.rawQuery(sql, null);
    if (cursor != null && cursor.moveToFirst()) {
        do {
            words.add(new Word(cursor.getInt(0), cursor.getString(1), cursor.getString(2)));
        } while (cursor.moveToNext());
        cursor.close();
    }
    db.close();
    return words;
}

Tổng số dòng có trong database:

public int getTotalWord() {
    SQLiteDatabase db = getReadableDatabase();
    String sql = "SELECT * FROM " + TABLE_WORD;
    Cursor cursor = db.rawQuery(sql, null);
    int totalRows = cursor.getCount();
    cursor.close();
    return totalRows;
}

Update data

Đối với việc cập nhật hay xóa dữ liệu giống như với việc chèn. SQLiteDatabaseHelper cung cấp cho các phương thức insert(), update()delete().

public int updateWord(Word word) {
    SQLiteDatabase db = getWritableDatabase();
    ContentValues values = new ContentValues();
    values.put(WORD_COLUMN, word.getWord());
    values.put(MEAN_COLUMN, word.getMean());
    int rowEffect = db.update(TABLE_WORD, values, ID_COLUMN + " = ?", new String[]{String.valueOf(word.getId())});
    db.close();
    return rowEffect;
}

Delete data

public int deleteWord(Word word) {
    SQLiteDatabase db = getReadableDatabase();
    int rowEffect = db.delete(TABLE_WORD, ID_COLUMN + " = ?", new String[]{String.valueOf(word.getId())});
    db.close();
    return rowEffect;
}

Demo các phương thức trên trong file MainActivity.java

package com.example.nguyennghia.databasedemo;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
import android.util.Log;
import java.util.List;

public class MainActivity extends AppCompatActivity {
    private static final String TAG = "MainActivity";

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

        // Get instance
        DatabaseHelper db = DatabaseHelper.getInstance(this);

        // Insert data
        db.insertWord(new Word("book", "Sách(n), đặt chỗ(v)"));
        db.insertWord(new Word("table", "Bàn(n)"));
        db.insertWord(new Word("action movie", "Phim hành động"));

        // Log all word in database
        for(Word w: db.getAllWord()){
            Log.e(TAG, "onCreate: " + w.getId() + ", " + w.getWord() + ", " + w.getMean());
        }

        // Update word
        Word word = db.getAllWord().get(0);
        word.setMean("Sách(n), đặt chỗ(v), đặt vé(v)");
        db.updateWord(word);

        // Log all word in database
        for(Word w: db.getAllWord()){
            Log.e(TAG, "onCreate: " + w.getId() + ", " + w.getWord() + ", " + w.getMean());
        }

        // Delete word
        db.deleteWord(db.getAllWord().get(0));

        // Log total rows in database
        Log.e(TAG, "onCreate: " + db.getTotalWord());
    }
}

Tìm thấy database tại đường dẫn:

database/data/[application package name]/databases/database_name

Database DICTIONARY_DB đã tạo:

DICTIONARY_DB

Tải source demo:

IO Stream

IO Stream Co., Ltd

30 Trinh Dinh Thao, Hoa Thanh ward, Tan Phu district, Ho Chi Minh city, Vietnam
+84 28 22 00 11 12
developer@iostream.co

383/1 Quang Trung, ward 10, Go Vap district, Ho Chi Minh city
Business license number: 0311563559 issued by the Department of Planning and Investment of Ho Chi Minh City on February 23, 2012

©IO Stream, 2013 - 2024