IndexedDB 처리용

손정만·2022년 1월 18일
1

프로젝트 진행하며 잠시 IndexedDB 사용할때
처리를 위해 만들었던 구조이다.

const DB_VERSION = 2;

let indexedDB = {
  db: null,
  ready: false,

  // collections: {},

  initialize: async (options) => {
    if (options.dbName === undefined) {
      return new Error('Must need DB name. {dbName:\'\'}');
    }

    if (!indexedDB.ready) {
      if (options.collectionName) {
        indexedDB.db = await indexedDB.get(options.dbName, options.collectionName);
        // indexedDB.collections[options.collectionName] = await indexedDB.collection.get(options.collectionName);
      } else {
        indexedDB.db = await indexedDB.get('mapImage');
      }
    } else {
      console.warn('Already initialized');
    }
    indexedDB.ready = true;
  },

  get: async (dbName, collectionName) => {
    return new Promise((resolve, reject) => {
      let request = window.indexedDB.open(dbName, DB_VERSION);

      request.onerror = (event) => {
        reject(new Error(event.target.error));
      };

      request.onsuccess = (event) => {
        let db = event.target.result;
        db.onversionchange = event => {
          console.warn('The version of this database has changed');
        };
        resolve(db);
      };

      request.onupgradeneeded = (event) => {
        let db = event.target.result;
        if (event.oldVersion !== 0 && event.oldVersion < event.newVersion &&
            db.name === dbName) {
          db.deleteObjectStore(collectionName);
        }
        let objectStore = db.createObjectStore(collectionName, {
          /* autoIncrement: true,
          keyPath: 'id' */
        });
        console.log('DB created', objectStore);
      };
    });
  },

  collection: {
    get: async (collectionName) => {
      return new Promise((resolve, reject) => {
        if (indexedDB.ready) {
          if (collectionName === undefined) {
            reject(new Error('Must need collection name.'));
          }
          let trans = indexedDB.db.transaction([collectionName], 'readonly');
          trans.oncomplete = e => {
            resolve(collection);
          };

          let store = trans.objectStore(collectionName);
          let collection = [];

          store.openCursor().onsuccess = e => {
            let cursor = e.target.result;
            if (cursor) {
              collection.push(cursor.value);
              cursor.continue();
            }
          };
        } else {
          reject(new Error('DB is not initialized'));
        }
      });
    }
  },

  item: {
    add: async (collectionName, id, item) => {
      return new Promise((resolve, reject) => {
        if (indexedDB.ready) {
          if (collectionName === undefined) {
            reject(new Error('Must need collection name.'));
          }
          if (id === undefined) {
            reject(new Error('Item ID is missing.'));
          }
          if (item === undefined) {
            reject(new Error('Item is missing.'));
          }

          let request = indexedDB.db.transaction([collectionName], 'readwrite')
            .objectStore(collectionName).add(item, id);
          request.onerror = async (event) => {
            reject(new Error(event.target.error));
          };
          request.onsuccess = (event) => {
            resolve(true);
          };
        } else {
          reject(new Error('DB is not initialized'));
        }
      });
    },
    get: async (collectionName, id) => {
      return new Promise((resolve, reject) => {
        if (indexedDB.ready) {
          if (collectionName === undefined) {
            reject(new Error('Must need collection name.'));
          }
          if (id === undefined) {
            reject(new Error('Item ID is missing.'));
          }

          let request = indexedDB.db.transaction([collectionName])
            .objectStore(collectionName).get(id);
          request.onerror = (event) => {
            reject(new Error(event.target.error));
          };
          request.onsuccess = (event) => {
            resolve(event.target.result);
          };
        } else {
          reject(new Error('DB is not initialized'));
        }
      });
    },
    update: async (collectionName, id, newItem) => {
      return new Promise((resolve, reject) => {
        if (indexedDB.ready) {
          if (collectionName === undefined) {
            reject(new Error('Must need collection name.'));
          }
          if (id === undefined) {
            reject(new Error('Item ID is missing.'));
          }
          if (newItem === undefined) {
            reject(new Error('Item is missing.'));
          }

          let request = indexedDB.db.transaction([collectionName], 'readwrite')
            .objectStore(collectionName).put(newItem, id);

          request.onerror = (event) => {
            reject(new Error(event.target.error));
          };
          request.onsuccess = (event) => {
            resolve(true);
          };
        } else {
          reject(new Error('DB is not initialized'));
        }
      });
    },
    delete: async (collectionName, id) => {
      return new Promise((resolve, reject) => {
        if (indexedDB.ready) {
          if (collectionName === undefined) {
            reject(new Error('Must need collection name.'));
          }
          if (id === undefined) {
            reject(new Error('Item ID is missing.'));
          }

          let request = indexedDB.db.transaction([collectionName], 'readwrite')
            .objectStore(collectionName).delete(id);
          request.onerror = (event) => {
            reject(new Error(event.target.error));
          };
          request.onsuccess = (event) => {
            resolve(true);
          };
        } else {
          reject(new Error('DB is not initialized'));
        }
      });
    }
  }
};

export default indexedDB;
import IndexedDB from './plugin/indexedDB';
Vue.prototype.$db = IndexedDB;

const COLLECTION = 'test';
const ID = 12544;

// DB 초기화
await this.$db.initialize({
  dbName: this.$db.NAME,
  collectionName: this.$db.COLLECTIONS.MAP_IMAGE
});

// 추가 (중복시, 에러발생)
await this.$db.item.add(COLLECTION, ID, {aaaa: 11});

// 조회
a = await this.$db.item.get(COLLECTION, ID);
console.log(a);

// 수정 (미존재시, 추가)
await this.$db.item.update(COLLECTION, ID, {aaaa: 11, bbbb: 22});

// 삭제
a = await this.$db.item.get(COLLECTION, ID);
console.log(a);

0개의 댓글