亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

為了賬號安全,請及時綁定郵箱和手機立即綁定

跟老衛學HarmonyOS開發:ArkTS關系型數據庫開發

本节以一个“账本”为例,使用关系型数据库的相关接口实现了对账单的增、删、改、查操作。

为了演示该功能,创建一个名为“ArkTSRdb”的应用,源码见文末。

操作RdbStore

首先要获取一个RdbStore来操作关系型数据库。

src/main/ets目录下创建名为“common/database”目录,用于存放常用的数据库相关的类。在该common/database目录创建工具类Rdb,代码如下:

import { relationalStore } from '@kit.ArkData';
import CommonConstants from '../constants/CommonConstants';

export default class Rdb {
  private rdbStore: relationalStore.RdbStore | null = null;
  private tableName: string;
  private sqlCreateTable: string;
  private columns: Array<string>;

  constructor(tableName: string, sqlCreateTable: string, columns: Array<string>) {
    this.tableName = tableName;
    this.sqlCreateTable = sqlCreateTable;
    this.columns = columns;
  }

  getRdbStore(callback: Function = () => {
  }) {
    if (!callback || typeof callback === 'undefined' || callback === undefined) {
      console.info('getRdbStore() has no callback!');
      return;
    }
    if (this.rdbStore !== null) {
      console.info('The rdbStore exists.');
      callback();
      return
    }
    let context: Context = getContext(this) as Context;
    relationalStore.getRdbStore(context, CommonConstants.STORE_CONFIG, (err, rdb) => {
      if (err) {
        console.error(`gerRdbStore() failed, err: ${err}`);
        return;
      }
      this.rdbStore = rdb;
      this.rdbStore.executeSql(this.sqlCreateTable);
      console.info('getRdbStore() finished.');
      callback();
    });
  }

  // ...
}

数据库所需要的配置存在以下common/constants/CommonConstants.ets文件中:

import { relationalStore } from '@kit.ArkData';

export default class CommonConstants {
  /**
   * Rdb database config.
   */
  static readonly STORE_CONFIG: relationalStore.StoreConfig = {
    name: 'database.db',
    securityLevel: relationalStore.SecurityLevel.S1
  };

}

为了对数据进行增、删、改、查操作,我们要封装对应接口。关系型数据库接口提供的增、删、改、查方法均有callback和Promise两种异步回调方式,本例子使用了callback异步回调。代码如下:

insertData(data: relationalStore.ValuesBucket, callback: Function = () => {
}) {
  if (!callback || typeof callback === 'undefined' || callback === undefined) {
    console.info('insertData() has no callback!');
    return;
  }
  let resFlag: boolean = false;
  const valueBucket: relationalStore.ValuesBucket = data;
  if (this.rdbStore) {
    this.rdbStore.insert(this.tableName, valueBucket, (err, ret) => {
      if (err) {
        console.error(`insertData() failed, err: ${err}`);
        callback(resFlag);
        return;
      }
      console.info(`insertData() finished: ${ret}`);
      callback(ret);
    });
  }
}

deleteData(predicates: relationalStore.RdbPredicates, callback: Function = () => {
}) {
  if (!callback || typeof callback === 'undefined' || callback === undefined) {
    console.info('deleteData() has no callback!');
    return;
  }
  let resFlag: boolean = false;
  if (this.rdbStore) {
    this.rdbStore.delete(predicates, (err, ret) => {
      if (err) {
        console.error(`deleteData() failed, err: ${err}`);
        callback(resFlag);
        return;
      }
      console.info(`deleteData() finished: ${ret}`);
      callback(!resFlag);
    });
  }
}

updateData(predicates: relationalStore.RdbPredicates, data: relationalStore.ValuesBucket, callback: Function = () => {
}) {
  if (!callback || typeof callback === 'undefined' || callback === undefined) {
    console.info('updateDate() has no callback!');
    return;
  }
  let resFlag: boolean = false;
  const valueBucket: relationalStore.ValuesBucket = data;
  if (this.rdbStore) {
    this.rdbStore.update(valueBucket, predicates, (err, ret) => {
      if (err) {
        console.error(`updateData() failed, err: ${err}`);
        callback(resFlag);
        return;
      }
      console.info(`updateData() finished: ${ret}`);
      callback(!resFlag);
    });
  }
}

query(predicates: relationalStore.RdbPredicates, callback: Function = () => {
}) {
  if (!callback || typeof callback === 'undefined' || callback === undefined) {
    console.info('query() has no callback!');
    return;
  }
  if (this.rdbStore) {
    this.rdbStore.query(predicates, this.columns, (err, resultSet) => {
      if (err) {
        console.error(`query() failed, err:  ${err}`);
        return;
      }
      console.info('query() finished.');
      callback(resultSet);
      resultSet.close();
    });
  }
}

账目信息的表示

由于需要记录账目的类型(收入/支出)、具体类别和金额,因此我们需要创建一张存储账目信息的表,SQL脚本下:

export default class CommonConstants {
  // ...
  
  /**
   * Account table config.
   */
  static readonly ACCOUNT_TABLE: TableConfig = {
    tableName: 'accountTable',
    sqlCreate: 'CREATE TABLE IF NOT EXISTS accountTable(id INTEGER PRIMARY KEY AUTOINCREMENT, accountType INTEGER, ' +
      'typeText TEXT, amount INTEGER)',
    columns: ['id', 'accountType', 'typeText', 'amount']
  };
}

interface TableConfig {
  tableName: string;
  sqlCreate: string;
  columns: Array<string>;
}

accountTable表的各字段含义如下:

  • id:主键。
  • accountType:账目类型。0表示支出;1表示收入。
  • typeText:账目的具体类别。
  • amount:账目金额。

src/main/ets目录下创建名为“viewmodel”目录,并在该目录下创建与上述脚本对应的类AccountData,代码如下:

export default class AccountData {
  id: number = -1;
  accountType: number = 0;
  typeText: string = '';
  amount: number = 0;
}

操作账目信息表

创建针对账目信息表的操作类common/database/tables/AccountTable.ets。AccountTable类封装了增、删、改、查接口。代码如下:

import { relationalStore } from '@kit.ArkData';
import AccountData from '../../../viewmodel/AccountData';
import CommonConstants from '../../constants/CommonConstants';
import Rdb from '../Rdb';

export default class AccountTable {
  private accountTable = new Rdb(CommonConstants.ACCOUNT_TABLE.tableName, CommonConstants.ACCOUNT_TABLE.sqlCreate,
    CommonConstants.ACCOUNT_TABLE.columns);

  constructor(callback: Function = () => {
  }) {
    this.accountTable.getRdbStore(callback);
  }

  getRdbStore(callback: Function = () => {
  }) {
    this.accountTable.getRdbStore(callback);
  }

  insertData(account: AccountData, callback: Function) {
    const valueBucket: relationalStore.ValuesBucket = generateBucket(account);
    this.accountTable.insertData(valueBucket, callback);
  }

  deleteData(account: AccountData, callback: Function) {
    let predicates = new relationalStore.RdbPredicates(CommonConstants.ACCOUNT_TABLE.tableName);
    predicates.equalTo('id', account.id);
    this.accountTable.deleteData(predicates, callback);
  }

  updateData(account: AccountData, callback: Function) {
    const valueBucket: relationalStore.ValuesBucket = generateBucket(account);
    let predicates = new relationalStore.RdbPredicates(CommonConstants.ACCOUNT_TABLE.tableName);
    predicates.equalTo('id', account.id);
    this.accountTable.updateData(predicates, valueBucket, callback);
  }

  query(amount: number, callback: Function, isAll: boolean = true) {
    let predicates = new relationalStore.RdbPredicates(CommonConstants.ACCOUNT_TABLE.tableName);
    if (!isAll) {
      predicates.equalTo('amount', amount);
    }
    this.accountTable.query(predicates, (resultSet: relationalStore.ResultSet) => {
      let count: number = resultSet.rowCount;
      if (count === 0 || typeof count === 'string') {
        console.log('Query no results!');
        callback([]);
      } else {
        resultSet.goToFirstRow();
        const result: AccountData[] = [];
        for (let i = 0; i < count; i++) {
          let tmp: AccountData = {
            id: 0, accountType: 0, typeText: '', amount: 0
          };
          tmp.id = resultSet.getDouble(resultSet.getColumnIndex('id'));
          tmp.accountType = resultSet.getDouble(resultSet.getColumnIndex('accountType'));
          tmp.typeText = resultSet.getString(resultSet.getColumnIndex('typeText'));
          tmp.amount = resultSet.getDouble(resultSet.getColumnIndex('amount'));
          result[i] = tmp;
          resultSet.goToNextRow();
        }
        callback(result);
      }
    });
  }
}

function generateBucket(account: AccountData): relationalStore.ValuesBucket {
  let obj: relationalStore.ValuesBucket = {};
  obj.accountType = account.accountType;
  obj.typeText = account.typeText;
  obj.amount = account.amount;
  return obj;
}

设计界面

为了简化程序,突出核心逻辑,我们的界面设计的非常简单,只是一个Text组件和四个Button组件。四个Button组件用于触发增、删、改、查操作,而Text组件用于展示每次操作后的结果。修改Index代码如下:

import AccountTable from '../common/database/tables/AccountTable';
import AccountData from '../viewmodel/AccountData';

@Entry
@Component
struct Index {
  @State message: string = 'Hello World'
  private accountTable = new AccountTable();

  build() {
    Row() {
      Column() {
        Text(this.message)
          .fontSize(50)
          .fontWeight(FontWeight.Bold)

        // 增加
        Button(('增加'), { type: ButtonType.Capsule })
          .width(140)
          .fontSize(40)
          .fontWeight(FontWeight.Medium)
          .margin({ top: 20, bottom: 20 })
          .onClick(() => {
            let newAccount: AccountData = { id: 1, accountType: 0, typeText: '苹果', amount: 0 };
            this.accountTable.insertData(newAccount, () => {
            })
          })

        // 查询
        Button(('查询'), { type: ButtonType.Capsule })
          .width(140)
          .fontSize(40)
          .fontWeight(FontWeight.Medium)
          .margin({ top: 20, bottom: 20 })
          .onClick(() => {
            this.accountTable.query(0, (result: AccountData[]) => {
              this.message = JSON.stringify(result);
            }, true);
          })

        // 修改
        Button(('修改'), { type: ButtonType.Capsule })
          .width(140)
          .fontSize(40)
          .fontWeight(FontWeight.Medium)
          .margin({ top: 20, bottom: 20 })
          .onClick(() => {
            let newAccount: AccountData = { id: 1, accountType: 1, typeText: '栗子', amount: 1 };
            this.accountTable.updateData(newAccount, () => {
            })
          })

        // 删除
        Button(('删除'), { type: ButtonType.Capsule })
          .width(140)
          .fontSize(40)
          .fontWeight(FontWeight.Medium)
          .margin({ top: 20, bottom: 20 })
          .onClick(() => {
            let newAccount: AccountData = { id: 1, accountType: 1, typeText: '栗子', amount: 1 };
            this.accountTable.deleteData(newAccount, () => {
            })
          })
      }
      .width('100%')
    }
    .height('100%')
  }
}

上述代码,在aboutToAppear生命周期阶段,初始化了数据库。点击“新增”会将预设好的数据“{ id: 1, accountType: 0, typeText: '苹果', amount: 0 }”写入到数据库。点击“修改”会将预设好的“{ id: 1, accountType: 1, typeText: '栗子', amount: 1 }”的数据更新到数据库。点击“删除”则会将预设好的“{ id: 1, accountType: 1, typeText: '栗子', amount: 1 }”的数据从数据库删除。

运行

运行应用显示的界面效果如下图10-3所示。

当用户点击“增加”后再点击“查询”时,界面如下图10-4所示,证明数据已经成功写入数据库。

当用户点击“修改”后再点击“查询”时,界面如下图10-5所示,证明数据已经被修改并更新回数据库。

当用户点击“删除”后再点击“查询”时,界面如下图10-6所示,证明数据已经从数据库删除。

源码

點擊查看更多內容
TA 點贊

若覺得本文不錯,就分享一下吧!

評論

作者其他優質文章

正在加載中
全棧工程師
手記
粉絲
1.7萬
獲贊與收藏
2192

關注作者,訂閱最新文章

閱讀免費教程

  • 推薦
  • 評論
  • 收藏
  • 共同學習,寫下你的評論
感謝您的支持,我會繼續努力的~
掃碼打賞,你說多少就多少
贊賞金額會直接到老師賬戶
支付方式
打開微信掃一掃,即可進行掃碼打賞哦
今天注冊有機會得

100積分直接送

付費專欄免費學

大額優惠券免費領

立即參與 放棄機會
微信客服

購課補貼
聯系客服咨詢優惠詳情

幫助反饋 APP下載

慕課網APP
您的移動學習伙伴

公眾號

掃描二維碼
關注慕課網微信公眾號

舉報

0/150
提交
取消