HarmonyOS 鸿蒙Next关系型数据库设计与操作
HarmonyOS 鸿蒙Next关系型数据库设计与操作 HarmonyOS 提供了哪些数据持久化方案?在需要存储结构化数据时,如何使用关系型数据库 RDB?请详细说明数据库的初始化、表的创建、数据的增删改查操作,以及如何处理数据库版本升级和字段迁移?(问题来源项目案例整理:https://github.com/heqiyuan35-creator/HydroQuiz.git)
HarmonyOS 数据持久化方案包括:Preferences(轻量键值对)、RDB(关系型数据库)、分布式数据管理等。
数据库初始化:
import { relationalStore } from '@kit.ArkData';
const config: relationalStore.StoreConfig = {
name: 'HydroQuiz.db',
securityLevel: relationalStore.SecurityLevel.S1
};
this.rdbStore = await relationalStore.getRdbStore(context, config);
创建表和索引:
const createTable: string = `
CREATE TABLE IF NOT EXISTS knowledge_read_records (
article_id TEXT PRIMARY KEY,
view_count INTEGER DEFAULT 0,
read_time INTEGER DEFAULT 0,
progress INTEGER DEFAULT 0,
last_read_time INTEGER NOT NULL
)
`;
await this.rdbStore.executeSql(createTable);
await this.rdbStore.executeSql('CREATE INDEX IF NOT EXISTS idx_read_time ON knowledge_read_records(last_read_time)');
CRUD 操作:
// 查询
const predicates = new relationalStore.RdbPredicates('knowledge_read_records');
predicates.equalTo('article_id', articleId);
const resultSet = await store.query(predicates);
// 插入
const valueBucket: relationalStore.ValuesBucket = {
article_id: articleId,
view_count: 1,
last_read_time: Date.now()
};
await store.insert('knowledge_read_records', valueBucket);
// 更新
await store.update(valueBucket, predicates);
// 删除
await store.delete(predicates);
版本升级迁移:
// 添加新字段(兼容旧版本)
try {
await this.rdbStore.executeSql('ALTER TABLE wrong_questions ADD COLUMN note TEXT DEFAULT \'\'');
} catch (e) {
// 字段已存在,忽略错误
}
更多关于HarmonyOS 鸿蒙Next关系型数据库设计与操作的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html
HarmonyOS Next提供了多种数据持久化方案,包括:轻量级偏好数据库(Preferences)、关系型数据库(RDB)以及分布式数据对象(DataObject)。对于需要存储结构化数据、支持复杂查询和事务的场景,关系型数据库(RDB)是首选方案。
以下是基于HarmonyOS Next的关系型数据库(RDB)设计与操作的核心步骤:
1. 数据库初始化与配置
首先,需要在module.json5文件中声明数据库的访问权限。
{
"module": {
"requestPermissions": [
{
"name": "ohos.permission.DISTRIBUTED_DATASYNC"
}
]
}
}
然后,在应用代码中通过RdbStoreConfig和RdbOpenCallback进行初始化。
import { relationalStore, RdbStore, RdbStoreConfig } from '@kit.RelationalStoreKit';
// 配置数据库
let config: RdbStoreConfig = {
name: 'myDatabase.db', // 数据库名称
securityLevel: relationalStore.SecurityLevel.S1 // 安全级别
};
// 定义数据库版本和表结构创建/升级逻辑
let openCallback: relationalStore.RdbOpenCallback = {
onOpen: (store: RdbStore) => {
console.info('RDB opened');
},
onCreate: (store: RdbStore) => {
// 首次创建数据库时执行
store.executeSql('CREATE TABLE IF NOT EXISTS USER (ID INTEGER PRIMARY KEY AUTOINCREMENT, NAME TEXT NOT NULL, AGE INTEGER)');
console.info('RDB created and table initialized');
},
onUpgrade: (store: RdbStore, oldVersion: number, newVersion: number) => {
// 数据库版本升级时执行,用于字段迁移
// 示例:从版本1升级到版本2,新增SCORE字段
if (oldVersion < 2) {
store.executeSql('ALTER TABLE USER ADD COLUMN SCORE INTEGER DEFAULT 0');
}
console.info(`RDB upgraded from v${oldVersion} to v${newVersion}`);
}
};
// 获取RDB实例
let rdbStore: RdbStore | undefined = undefined;
try {
relationalStore.getRdbStore(context, config).then((store: RdbStore) => {
rdbStore = store;
console.info('RDB store obtained');
});
} catch (err) {
console.error(`Failed to get RDB store. Code:${err.code}, message:${err.message}`);
}
2. 数据操作(增删改查)
假设已初始化rdbStore实例,并存在USER表。
插入数据(Create)
import { ValuesBucket } from '@kit.RelationalStoreKit';
let valueBucket: ValuesBucket = {
'NAME': '张三',
'AGE': 25,
'SCORE': 90
};
try {
let rowId = await rdbStore.insert('USER', valueBucket);
console.info(`Insert succeeded, rowId: ${rowId}`);
} catch (err) {
console.error(`Insert failed. Code:${err.code}, message:${err.message}`);
}
查询数据(Read)
import { RdbPredicates } from '@kit.RelationalStoreKit';
let predicates = new relationalStore.RdbPredicates('USER');
predicates.equalTo('NAME', '张三'); // 查询条件:NAME = '张三'
try {
let resultSet = await rdbStore.query(predicates, ['ID', 'NAME', 'AGE', 'SCORE']);
console.info(`Query succeeded, resultSet row count: ${resultSet.rowCount}`);
while (resultSet.goToNextRow()) {
let id = resultSet.getDouble(resultSet.getColumnIndex('ID'));
let name = resultSet.getString(resultSet.getColumnIndex('NAME'));
let age = resultSet.getLong(resultSet.getColumnIndex('AGE'));
let score = resultSet.getLong(resultSet.getColumnIndex('SCORE'));
console.info(`ID: ${id}, NAME: ${name}, AGE: ${age}, SCORE: ${score}`);
}
resultSet.close();
} catch (err) {
console.error(`Query failed. Code:${err.code}, message:${err.message}`);
}
更新数据(Update)
let updateValues: ValuesBucket = {
'AGE': 26,
'SCORE': 95
};
let updatePredicates = new relationalStore.RdbPredicates('USER');
updatePredicates.equalTo('NAME', '张三');
try {
let rowsUpdated = await rdbStore.update(updateValues, updatePredicates);
console.info(`Update succeeded, updated rows: ${rowsUpdated}`);
} catch (err) {
console.error(`Update failed. Code:${err.code}, message:${err.message}`);
}
删除数据(Delete)
let deletePredicates = new relationalStore.RdbPredicates('USER');
deletePredicates.equalTo('NAME', '张三');
try {
let rowsDeleted = await rdbStore.delete(deletePredicates);
console.info(`Delete succeeded, deleted rows: ${rowsDeleted}`);
} catch (err) {
console.error(`Delete failed. Code:${err.code}, message:${err.message}`);
}
3. 数据库版本升级与字段迁移
如初始化代码所示,在RdbOpenCallback的onUpgrade方法中处理版本升级。通过比较oldVersion和newVersion,使用ALTER TABLE语句执行字段添加、修改或删除。对于复杂的迁移(如修改字段类型、拆分表),可能需要创建新表、迁移数据后删除旧表。
关键点:
- 在
RdbStoreConfig中通过version字段指定数据库版本号。 onUpgrade方法在数据库版本号增加时自动触发。- 字段迁移操作应包裹在事务中以保证数据一致性。
总结
HarmonyOS Next的RDB提供了完整的关系型数据库操作能力,通过RdbStore API进行初始化、建表、增删改查。版本升级和字段迁移逻辑在RdbOpenCallback.onUpgrade中实现,需谨慎处理以保障数据完整性。


