|
|
@@ -1,4 +1,3 @@
|
|
|
-
|
|
|
import relationalStore from '@ohos.data.relationalStore';
|
|
|
import { LogUtil, StrUtil } from '@pura/harmony-utils';
|
|
|
import Logger from './Logger';
|
|
|
@@ -52,10 +51,16 @@ export default class RdbUtils {
|
|
|
' parentPath TEXT,\n' +
|
|
|
' isFav INTEGER,\n' +
|
|
|
' pixelMapPath TEXT,\n' +
|
|
|
- ' pixelMapToString TEXT' +
|
|
|
-
|
|
|
+ ' pixelMapToString TEXT,\n' +
|
|
|
+ ' duration TEXT,\n' +
|
|
|
+ ' sampleRate TEXT,\n' +
|
|
|
+ ' playCount INTEGER DEFAULT 0,\n' +
|
|
|
+ ' lastPlayedStr TEXT,\n' +
|
|
|
+ ' trackCount TEXT,\n' +
|
|
|
+ ' lyricContent TEXT,\n' +
|
|
|
+ ' mimeType TEXT' +
|
|
|
')',
|
|
|
- columns: ['id', 'name', 'filePath','mtype', 'videoSize', 'cTime','size', 'artist', 'album','fileName','parentPath','isFav','pixelMapPath','pixelMapToString']
|
|
|
+ columns: ['id', 'name', 'filePath','mtype', 'videoSize', 'cTime','size', 'artist', 'album','fileName','parentPath','isFav','pixelMapPath','pixelMapToString', 'duration', 'mimeType', 'trackCount', 'sampleRate', 'lastPlayedStr', 'playCount', 'lyricContent']
|
|
|
};
|
|
|
|
|
|
constructor(tableName: string, sqlCreateTable: string, columns: Array<string>) {
|
|
|
@@ -77,46 +82,95 @@ export default class RdbUtils {
|
|
|
callback();
|
|
|
return
|
|
|
}
|
|
|
- // let context: Context = getContext(this) as Context;
|
|
|
+
|
|
|
relationalStore.getRdbStore(context, RdbUtils.STORE_CONFIG, (err, rdb) => {
|
|
|
if (err) {
|
|
|
Logger.error(RdbUtils.RDB_TAG, `gerRdbStore() failed, err: ${err}`);
|
|
|
return;
|
|
|
}
|
|
|
this.rdbStore = rdb;
|
|
|
+
|
|
|
+ // 先创建表(如果不存在)
|
|
|
this.rdbStore.executeSql(this.sqlCreateTable);
|
|
|
- if (this.rdbStore.version == 0) {
|
|
|
- // 升级到版本1,添加列
|
|
|
- // ✅ SQLite要求每列单独执行ALTER TABLE
|
|
|
- const alterColumns = [
|
|
|
- "ALTER TABLE mediaTable ADD COLUMN duration TEXT",
|
|
|
- "ALTER TABLE mediaTable ADD COLUMN sampleRate TEXT",
|
|
|
- "ALTER TABLE mediaTable ADD COLUMN playCount INTEGER DEFAULT 0",
|
|
|
- "ALTER TABLE mediaTable ADD COLUMN lastPlayedStr TEXT",
|
|
|
- "ALTER TABLE mediaTable ADD COLUMN trackCount TEXT",
|
|
|
- "ALTER TABLE mediaTable ADD COLUMN lyricContent TEXT",
|
|
|
- "ALTER TABLE mediaTable ADD COLUMN mimeType TEXT"
|
|
|
- ];
|
|
|
- try {
|
|
|
- // 逐列执行添加
|
|
|
- alterColumns.forEach(sql => {
|
|
|
- if(this.rdbStore)
|
|
|
- this.rdbStore.executeSql(sql);
|
|
|
- });
|
|
|
- this.rdbStore.version = 1
|
|
|
- LogUtil.info('onecold Upgrade database from version 0 to 1 success.');
|
|
|
- } catch (e) {
|
|
|
- Logger.error(RdbUtils.RDB_TAG, `Upgrade database failed: ${e}`);
|
|
|
- // 注意:升级失败,可能需要处理,这里我们记录错误,但继续执行回调
|
|
|
- }
|
|
|
+
|
|
|
+ // 检查数据库版本并更新列
|
|
|
+ try {
|
|
|
+ // 检查表结构
|
|
|
+ this.checkAndUpdateTableColumns();
|
|
|
+ Logger.info(RdbUtils.RDB_TAG, `数据库表结构检查完成`);
|
|
|
+ } catch (e) {
|
|
|
+ Logger.error(RdbUtils.RDB_TAG, `检查表结构时出错: ${e.message}`);
|
|
|
}
|
|
|
|
|
|
-
|
|
|
- // Logger.info(RdbUtils.RDB_TAG, 'getRdbStore() finished.');
|
|
|
callback();
|
|
|
});
|
|
|
}
|
|
|
-
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 检查并更新表列结构
|
|
|
+ * 使用表信息查询和ALTER TABLE添加缺失的列
|
|
|
+ */
|
|
|
+ private checkAndUpdateTableColumns() {
|
|
|
+ if (!this.rdbStore) {
|
|
|
+ Logger.error(RdbUtils.RDB_TAG, `数据库连接未初始化`);
|
|
|
+ return;
|
|
|
+ }
|
|
|
+
|
|
|
+ try {
|
|
|
+ // 查询表信息获取现有列
|
|
|
+ const tableInfoQuery = `PRAGMA table_info(${this.tableName})`;
|
|
|
+ // 使用Promise模式代替回调
|
|
|
+ this.rdbStore.executeSql(tableInfoQuery)
|
|
|
+ .then(() => {
|
|
|
+ // 定义应该存在的列及其类型
|
|
|
+ const requiredColumns: Record<string, string> = {
|
|
|
+ 'duration': 'TEXT',
|
|
|
+ 'sampleRate': 'TEXT',
|
|
|
+ 'playCount': 'INTEGER DEFAULT 0',
|
|
|
+ 'lastPlayedStr': 'TEXT',
|
|
|
+ 'trackCount': 'TEXT',
|
|
|
+ 'lyricContent': 'TEXT',
|
|
|
+ 'mimeType': 'TEXT'
|
|
|
+ };
|
|
|
+
|
|
|
+ // 逐个添加列,不依赖于检查结果
|
|
|
+ if (this.rdbStore) {
|
|
|
+ // 遍历映射
|
|
|
+ const columnEntries = Object.keys(requiredColumns);
|
|
|
+ for (let i = 0; i < columnEntries.length; i++) {
|
|
|
+ const column = columnEntries[i];
|
|
|
+ const type = requiredColumns[column];
|
|
|
+
|
|
|
+ const alterSql = `ALTER TABLE ${this.tableName} ADD COLUMN ${column} ${type}`;
|
|
|
+ try {
|
|
|
+ // 对每个列使用Promise模式
|
|
|
+ this.rdbStore.executeSql(alterSql)
|
|
|
+ .then(() => {
|
|
|
+ Logger.info(RdbUtils.RDB_TAG, `成功添加列: ${column}`);
|
|
|
+ })
|
|
|
+ .catch((alterErr: Error) => {
|
|
|
+ // 列可能已经存在,这是预期的错误
|
|
|
+ Logger.info(RdbUtils.RDB_TAG, `列 ${column} 可能已存在: ${alterErr.message}`);
|
|
|
+ });
|
|
|
+ } catch (e) {
|
|
|
+ Logger.error(RdbUtils.RDB_TAG, `添加列 ${column} 出错: ${e.message}`);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ // 设置数据库版本
|
|
|
+ if (this.rdbStore) {
|
|
|
+ this.rdbStore.version = 1;
|
|
|
+ Logger.info(RdbUtils.RDB_TAG, `数据库升级完成,版本设置为 1`);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ })
|
|
|
+ .catch((err: Error) => {
|
|
|
+ Logger.error(RdbUtils.RDB_TAG, `获取表信息失败: ${err.message}`);
|
|
|
+ });
|
|
|
+ } catch (e) {
|
|
|
+ Logger.error(RdbUtils.RDB_TAG, `检查表结构时出错: ${e.message}`);
|
|
|
+ }
|
|
|
+ }
|
|
|
|
|
|
//检查是否存在相同id的记录,存在则不插入,进一步判断pixelMapPath字段,如果旧值为空而新值不为空,则更新该字段。
|
|
|
async insertData(data: relationalStore.ValuesBucket, callback: Function = () => {},cover_api?:string) {
|
|
|
@@ -253,15 +307,22 @@ export default class RdbUtils {
|
|
|
Logger.info(RdbUtils.RDB_TAG, 'query() has no callback!');
|
|
|
return;
|
|
|
}
|
|
|
+
|
|
|
if (this.rdbStore) {
|
|
|
- this.rdbStore.query(predicates, this.columns, (err, resultSet) => {
|
|
|
+ // 使用安全的列集合查询
|
|
|
+ // 首先仅查询基本列(确保100%存在)
|
|
|
+ const safeColumns = ['id', 'name', 'filePath', 'mtype', 'videoSize', 'cTime',
|
|
|
+ 'size', 'artist', 'album', 'fileName', 'parentPath',
|
|
|
+ 'isFav', 'pixelMapPath', 'pixelMapToString'];
|
|
|
+
|
|
|
+ this.rdbStore.query(predicates, safeColumns, (err, resultSet) => {
|
|
|
if (err) {
|
|
|
- Logger.error(RdbUtils.RDB_TAG, `query() failed, err: ${err}`);
|
|
|
+ Logger.error(RdbUtils.RDB_TAG, `query() failed, err: ${err}`);
|
|
|
+ callback(null);
|
|
|
return;
|
|
|
}
|
|
|
- // Logger.info(RdbUtils.RDB_TAG, 'query() finished.');
|
|
|
+
|
|
|
callback(resultSet);
|
|
|
- resultSet.close();
|
|
|
});
|
|
|
}
|
|
|
}
|