使用indexDB封装简易的增删改查


class IndexDB {
  constructor(props) {
    const { dataBaseName, version, stores } = props;
    this.dataBaseName = dataBaseName;
    this.version = version;
    this.stores = stores;
    this.init_success = false
    this.db = null;
    this.init_promise = this.init();

  }
  init() {
    return new Promise((resolve, reject) => {
      var request = window.indexedDB.open(this.dataBaseName, this.version);
      request.onerror = (event) => {
        console.log('数据库打开报错', event.target.error);
        reject(event.target.error)
      };
      request.onsuccess = (event) => {
        this.db = request.result;
        console.log('数据库打开成功');
        resolve(true)
        this.init_success = true;
      };
      
      // 数据库升级事件
      request.onupgradeneeded = (event) => {
        let db = event.target.result;
        const transaction = event.target.transaction;
        // 创建或升级 store
        this.stores.forEach(({ name, keyPath, indexes }) => {
          if (!db.objectStoreNames.contains(name)) {
            let store;

            // 创建或获取对象仓库
            if (!db.objectStoreNames.contains(name)) {
              store = db.createObjectStore(name, { keyPath });
            } else {
              store = transaction.objectStore(name);
            }

            // 创建缺失的索引
            indexes?.forEach(({ name: indexName, keyPath: indexKeyPath, options }) => {
              if (!store.indexNames.contains(indexName)) {
                store.createIndex(indexName, indexKeyPath, options);
              }
            });
          }
        });

      };
    })

  }

  async ready() {
    if (!this.init_success) {
      await this.init_promise;
    }
    return this.db;
  }

  async add(storeName, data) {
    const db = await this.ready()
    return new Promise((resolve, reject) => {
     let transaction = db.transaction([storeName], 'readwrite');
     let objectStore = transaction.objectStore(storeName)
      var request = objectStore.add(data);

      request.onsuccess = function (event) {
        console.log('数据写入成功');
        resolve(true)
      };

      request.onerror = function (event) {
        console.log('数据写入失败', event.target.error);
        reject(event.target.error)
      }
    })

  }

  async get(storeName, key) {

    const db = await this.ready()

    return new Promise((resolve, reject) => {
      var transaction = db.transaction([storeName]);
      var objectStore = transaction.objectStore(storeName);
      var request = objectStore.get(key);

      request.onerror = (event) => {
        reject('事务失败');
      };

      request.onsuccess = (event) => {
        if (request.result) {
          resolve(request.result)
        } else {
          reject(null)
        }
      };
    })

  }

  async getByIndex(storeName, indexName, value) {

    const db = await this.ready()

    return new Promise((resolve, reject) => {
      var transaction = db.transaction([storeName], 'readonly');
      var store = transaction.objectStore(storeName);

      var index = store?.index(indexName);
      var request = index.get(value);

      request.onsuccess = (e) => {
        var result = e.target.result;
        if (result) {
          resolve(result)
        } else {
          resolve(null)
        }
      }
      request.onerror = (event) => {
        reject('事务失败');
      };

    })

  }

  async getAll(storeName) {
    const db = await this.ready()

    return new Promise((resolve, reject) => {
      var objectStore = db.transaction(storeName).objectStore(storeName);
      let list = []
      objectStore.openCursor().onsuccess = (event) => {
        var cursor = event.target.result;

        if (cursor) {
          list.push({
            ...cursor.value,
            _key: cursor.key,

          })
          cursor.continue();
        } else {
          resolve(list)
          console.log('没有更多数据了!');
        }
      };
    })

  }

  async update(storeName, data) {
    const db = await this.ready();
    // const result = await 
    return new Promise((resolve, reject) => {
      var request = db.transaction([storeName], 'readwrite')
        .objectStore(storeName)
        .put(data);

      request.onsuccess = function (event) {
        console.log('数据更新成功');
        resolve(true)
      };

      request.onerror = function (event) {
        console.log('数据更新失败');
        reject()
      }
    })

  }

  async remove(storeName, key) {
    const db = await this.ready();
    return new Promise((resolve, reject) => {
      var request = db.transaction([storeName], 'readwrite')
        .objectStore(storeName)
        .delete(key);
      console.log(request)

      request.onsuccess = function (event) {
        console.log('数据删除成功', event, `数据删除成功,主键: ${key}`);
        resolve(true)
      };
      request.onerror = function (event) {
        console.log('数据删除失败', event.target.error);
        reject(event.target.error)
      }
    })

  }

 // 关闭数据库
async close() {
  const db = await this.ready();
  return new Promise((resolve, reject) => {
   try {
    db.close();
    resolve(true)
   } catch (error) {
    reject(null)
   }
  })
}

}

export default IndexDB

在react页面中我们可以这样初始化(可以在componentDidMount生命周期中):

  try {
      this.indexDB = new IndexDB({
        dataBaseName: 'myDatabase', 
        version:5, 
        stores: [
        {
          name: 'users',
          keyPath: 'id',
          indexes: [
            {name: 'name',keyPath: 'name', options: { unique: false }  },
            { name: 'email', keyPath: 'email', options: { unique: true } },
            { name: 'age', keyPath: 'age' },
            { name: 'sex', keyPath: 'sex' }
          ]
        }
      ]
      });
  } catch {}
//添加数据:
andleAdd =  () => {
    this.indexDB.add('users', {
      id: 6,
      name: 'heshanwan',
      email: 'john@example.com33777664',
      age: 323,
      sex: 'man'
    });
  };
  
  //更新数据
   handleUpdate =  () => {
    this.indexDB.update('users', {
      id: 1,
      name: 'heshanwan22222222',
      email: 'john@example.com22222',
      age: 3232222
    }).then(res => console.log(res, '修改成功'));
  };
  
  
  //获取单条数据
  this.indexDB.get('users', 1)
            .then(res => {
              console.log(res, 'ressss----read')
            })
  // 或者
  this.indexDB.getByIndex('users', 'name', 'heshanwan2')
            .then(res => {
              console.log(res, 'ressss----read')
            })
  //获取所有数据
   this.indexDB.getAll('users')
            .then(res => {
              console.log(res, 'ressss----read')
            })
    //删除数据
     this.indexDB.remove('users', 3)
            .then(res => {
              console.log(res, 'ressss----read')
            })
posted @ 2025-04-21 23:19  heshanwan  阅读(56)  评论(0)    收藏  举报