base_object_store.go raw

   1  //go:build js && wasm
   2  // +build js,wasm
   3  
   4  package idb
   5  
   6  import (
   7  	"github.com/hack-pad/safejs"
   8  )
   9  
  10  // baseObjectStore is the common implementation for both object stores and indexes.
  11  type baseObjectStore struct {
  12  	txn           *Transaction
  13  	jsObjectStore safejs.Value
  14  }
  15  
  16  func wrapBaseObjectStore(txn *Transaction, jsObjectStore safejs.Value) *baseObjectStore {
  17  	if txn == nil {
  18  		txn = (*Transaction)(nil)
  19  	}
  20  	return &baseObjectStore{
  21  		txn:           txn,
  22  		jsObjectStore: jsObjectStore,
  23  	}
  24  }
  25  
  26  // Count returns a UintRequest, and, in a separate thread, returns the total number of records in the store or index.
  27  func (b *baseObjectStore) Count() (*UintRequest, error) {
  28  	reqValue, err := b.jsObjectStore.Call("count")
  29  	if err != nil {
  30  		return nil, tryAsDOMException(err)
  31  	}
  32  	req := wrapRequest(b.txn, reqValue)
  33  	return newUintRequest(req), nil
  34  }
  35  
  36  // CountKey returns a UintRequest, and, in a separate thread, returns the total number of records that match the provided key.
  37  func (b *baseObjectStore) CountKey(key safejs.Value) (*UintRequest, error) {
  38  	reqValue, err := b.jsObjectStore.Call("count", key)
  39  	if err != nil {
  40  		return nil, tryAsDOMException(err)
  41  	}
  42  	req := wrapRequest(b.txn, reqValue)
  43  	return newUintRequest(req), nil
  44  }
  45  
  46  // CountRange returns a UintRequest, and, in a separate thread, returns the total number of records that match the provided KeyRange.
  47  func (b *baseObjectStore) CountRange(keyRange *KeyRange) (*UintRequest, error) {
  48  	reqValue, err := b.jsObjectStore.Call("count", keyRange.jsKeyRange)
  49  	if err != nil {
  50  		return nil, tryAsDOMException(err)
  51  	}
  52  	req := wrapRequest(b.txn, reqValue)
  53  	return newUintRequest(req), nil
  54  }
  55  
  56  // GetAllKeys returns an ArrayRequest that retrieves record keys for all objects in the object store or index.
  57  func (b *baseObjectStore) GetAllKeys() (*ArrayRequest, error) {
  58  	reqValue, err := b.jsObjectStore.Call("getAllKeys")
  59  	if err != nil {
  60  		return nil, tryAsDOMException(err)
  61  	}
  62  	req := wrapRequest(b.txn, reqValue)
  63  	return newArrayRequest(req), nil
  64  }
  65  
  66  // GetAllKeysRange returns an ArrayRequest that retrieves record keys for all objects in the object store or index matching the specified query. If maxCount is 0, retrieves all objects matching the query.
  67  func (b *baseObjectStore) GetAllKeysRange(query *KeyRange, maxCount uint) (*ArrayRequest, error) {
  68  	args := []interface{}{query.jsKeyRange}
  69  	if maxCount > 0 {
  70  		args = append(args, maxCount)
  71  	}
  72  	reqValue, err := b.jsObjectStore.Call("getAllKeys", args...)
  73  	if err != nil {
  74  		return nil, tryAsDOMException(err)
  75  	}
  76  	req := wrapRequest(b.txn, reqValue)
  77  	return newArrayRequest(req), nil
  78  }
  79  
  80  // Get returns a Request, and, in a separate thread, returns the objects selected by the specified key. This is for retrieving specific records from an object store or index.
  81  func (b *baseObjectStore) Get(key safejs.Value) (*Request, error) {
  82  	reqValue, err := b.jsObjectStore.Call("get", key)
  83  	if err != nil {
  84  		return nil, tryAsDOMException(err)
  85  	}
  86  	return wrapRequest(b.txn, reqValue), nil
  87  }
  88  
  89  // GetKey returns a Request, and, in a separate thread retrieves and returns the record key for the object matching the specified parameter.
  90  func (b *baseObjectStore) GetKey(value safejs.Value) (*Request, error) {
  91  	reqValue, err := b.jsObjectStore.Call("getKey", value)
  92  	if err != nil {
  93  		return nil, tryAsDOMException(err)
  94  	}
  95  	return wrapRequest(b.txn, reqValue), nil
  96  }
  97  
  98  // OpenCursor returns a CursorWithValueRequest, and, in a separate thread, returns a new CursorWithValue. Used for iterating through an object store or index by primary key with a cursor.
  99  func (b *baseObjectStore) OpenCursor(direction CursorDirection) (*CursorWithValueRequest, error) {
 100  	reqValue, err := b.jsObjectStore.Call("openCursor", safejs.Null(), direction.jsValue())
 101  	if err != nil {
 102  		return nil, tryAsDOMException(err)
 103  	}
 104  	req := wrapRequest(b.txn, reqValue)
 105  	return newCursorWithValueRequest(req), nil
 106  }
 107  
 108  // OpenCursorKey is the same as OpenCursor, but opens a cursor over the given key instead.
 109  func (b *baseObjectStore) OpenCursorKey(key safejs.Value, direction CursorDirection) (*CursorWithValueRequest, error) {
 110  	reqValue, err := b.jsObjectStore.Call("openCursor", key, direction.jsValue())
 111  	if err != nil {
 112  		return nil, tryAsDOMException(err)
 113  	}
 114  	req := wrapRequest(b.txn, reqValue)
 115  	return newCursorWithValueRequest(req), nil
 116  }
 117  
 118  // OpenCursorRange is the same as OpenCursor, but opens a cursor over the given range instead.
 119  func (b *baseObjectStore) OpenCursorRange(keyRange *KeyRange, direction CursorDirection) (*CursorWithValueRequest, error) {
 120  	reqValue, err := b.jsObjectStore.Call("openCursor", keyRange.jsKeyRange, direction.jsValue())
 121  	if err != nil {
 122  		return nil, tryAsDOMException(err)
 123  	}
 124  	req := wrapRequest(b.txn, reqValue)
 125  	return newCursorWithValueRequest(req), nil
 126  }
 127  
 128  // OpenKeyCursor returns a CursorRequest, and, in a separate thread, returns a new Cursor. Used for iterating through all keys in an object store or index.
 129  func (b *baseObjectStore) OpenKeyCursor(direction CursorDirection) (*CursorRequest, error) {
 130  	reqValue, err := b.jsObjectStore.Call("openKeyCursor", safejs.Null(), direction.jsValue())
 131  	if err != nil {
 132  		return nil, tryAsDOMException(err)
 133  	}
 134  	req := wrapRequest(b.txn, reqValue)
 135  	return newCursorRequest(req), nil
 136  }
 137  
 138  // OpenKeyCursorKey is the same as OpenKeyCursor, but opens a cursor over the given key instead.
 139  func (b *baseObjectStore) OpenKeyCursorKey(key safejs.Value, direction CursorDirection) (*CursorRequest, error) {
 140  	reqValue, err := b.jsObjectStore.Call("openKeyCursor", key, direction.jsValue())
 141  	if err != nil {
 142  		return nil, tryAsDOMException(err)
 143  	}
 144  	req := wrapRequest(b.txn, reqValue)
 145  	return newCursorRequest(req), nil
 146  }
 147  
 148  // OpenKeyCursorRange is the same as OpenKeyCursor, but opens a cursor over the given key range instead.
 149  func (b *baseObjectStore) OpenKeyCursorRange(keyRange *KeyRange, direction CursorDirection) (*CursorRequest, error) {
 150  	reqValue, err := b.jsObjectStore.Call("openKeyCursor", keyRange.jsKeyRange, direction.jsValue())
 151  	if err != nil {
 152  		return nil, tryAsDOMException(err)
 153  	}
 154  	req := wrapRequest(b.txn, reqValue)
 155  	return newCursorRequest(req), nil
 156  }
 157