1 /*
2  * Copyright (C) 2010 Google Inc. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  *
8  * 1.  Redistributions of source code must retain the above copyright
9  *     notice, this list of conditions and the following disclaimer.
10  * 2.  Redistributions in binary form must reproduce the above copyright
11  *     notice, this list of conditions and the following disclaimer in the
12  *     documentation and/or other materials provided with the distribution.
13  *
14  * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
15  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
16  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17  * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
18  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
19  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
20  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
21  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
23  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24  */
25 
26 #ifndef THIRD_PARTY_BLINK_RENDERER_MODULES_INDEXEDDB_IDB_DATABASE_H_
27 #define THIRD_PARTY_BLINK_RENDERER_MODULES_INDEXEDDB_IDB_DATABASE_H_
28 
29 #include <memory>
30 
31 #include "base/memory/scoped_refptr.h"
32 #include "third_party/blink/public/mojom/feature_observer/feature_observer.mojom-blink.h"
33 #include "third_party/blink/renderer/bindings/core/v8/active_script_wrappable.h"
34 #include "third_party/blink/renderer/bindings/core/v8/string_or_string_sequence.h"
35 #include "third_party/blink/renderer/bindings/modules/v8/v8_idb_object_store_parameters.h"
36 #include "third_party/blink/renderer/bindings/modules/v8/v8_idb_transaction_options.h"
37 #include "third_party/blink/renderer/core/dom/dom_string_list.h"
38 #include "third_party/blink/renderer/core/execution_context/execution_context_lifecycle_observer.h"
39 #include "third_party/blink/renderer/modules/event_modules.h"
40 #include "third_party/blink/renderer/modules/event_target_modules.h"
41 #include "third_party/blink/renderer/modules/indexeddb/idb_database_callbacks.h"
42 #include "third_party/blink/renderer/modules/indexeddb/idb_metadata.h"
43 #include "third_party/blink/renderer/modules/indexeddb/idb_object_store.h"
44 #include "third_party/blink/renderer/modules/indexeddb/idb_transaction.h"
45 #include "third_party/blink/renderer/modules/indexeddb/indexed_db.h"
46 #include "third_party/blink/renderer/modules/indexeddb/web_idb_database.h"
47 #include "third_party/blink/renderer/modules/indexeddb/web_idb_database_callbacks.h"
48 #include "third_party/blink/renderer/modules/modules_export.h"
49 #include "third_party/blink/renderer/platform/bindings/script_state.h"
50 #include "third_party/blink/renderer/platform/heap/handle.h"
51 #include "third_party/blink/renderer/platform/scheduler/public/frame_or_worker_scheduler.h"
52 
53 namespace blink {
54 
55 class DOMException;
56 class ExceptionState;
57 class ExecutionContext;
58 class IDBObservation;
59 class IDBObserver;
60 
61 class MODULES_EXPORT IDBDatabase final
62     : public EventTargetWithInlineData,
63       public ActiveScriptWrappable<IDBDatabase>,
64       public ExecutionContextLifecycleObserver {
65   USING_GARBAGE_COLLECTED_MIXIN(IDBDatabase);
66   DEFINE_WRAPPERTYPEINFO();
67 
68  public:
69   IDBDatabase(
70       ExecutionContext*,
71       std::unique_ptr<WebIDBDatabase>,
72       IDBDatabaseCallbacks*,
73       v8::Isolate*,
74       mojo::PendingRemote<mojom::blink::ObservedFeature> connection_lifetime);
75   ~IDBDatabase() override;
76 
77   void Trace(Visitor*) override;
78 
79   // Overwrites the database metadata, including object store and index
80   // metadata. Used to pass metadata to the database when it is opened.
81   void SetMetadata(const IDBDatabaseMetadata&);
82   // Overwrites the database's own metadata, but does not change object store
83   // and index metadata. Used to revert the database's metadata when a
84   // versionchage transaction is aborted.
85   void SetDatabaseMetadata(const IDBDatabaseMetadata&);
86   void TransactionCreated(IDBTransaction*);
87   void TransactionFinished(const IDBTransaction*);
88   const String& GetObjectStoreName(int64_t object_store_id) const;
89   int32_t AddObserver(IDBObserver*,
90                       int64_t transaction_id,
91                       bool include_transaction,
92                       bool no_records,
93                       bool values,
94                       std::bitset<kIDBOperationTypeCount> operation_types);
95   void RemoveObservers(const Vector<int32_t>& observer_ids);
96 
97   // Implement the IDL
name()98   const String& name() const { return metadata_.name; }
version()99   uint64_t version() const { return metadata_.version; }
100   DOMStringList* objectStoreNames() const;
101 
createObjectStore(const String & name,const IDBObjectStoreParameters * options,ExceptionState & exception_state)102   IDBObjectStore* createObjectStore(const String& name,
103                                     const IDBObjectStoreParameters* options,
104                                     ExceptionState& exception_state) {
105     return createObjectStore(name, IDBKeyPath(options->keyPath()),
106                              options->autoIncrement(), exception_state);
107   }
108   IDBTransaction* transaction(ScriptState*,
109                               const StringOrStringSequence& store_names,
110                               const String& mode,
111                               ExceptionState&);
112   IDBTransaction* transaction(ScriptState*,
113                               const StringOrStringSequence& store_names,
114                               const String& mode,
115                               const IDBTransactionOptions* options,
116                               ExceptionState&);
117   void deleteObjectStore(const String& name, ExceptionState&);
118   void close();
119 
120   DEFINE_ATTRIBUTE_EVENT_LISTENER(abort, kAbort)
121   DEFINE_ATTRIBUTE_EVENT_LISTENER(close, kClose)
122   DEFINE_ATTRIBUTE_EVENT_LISTENER(error, kError)
123   DEFINE_ATTRIBUTE_EVENT_LISTENER(versionchange, kVersionchange)
124 
125   // IDBDatabaseCallbacks
126   void OnVersionChange(int64_t old_version, int64_t new_version);
127   void OnAbort(int64_t, DOMException*);
128   void OnComplete(int64_t);
129   void OnChanges(const WebIDBDatabaseCallbacks::ObservationIndexMap&,
130                  Vector<Persistent<IDBObservation>> observations,
131                  const WebIDBDatabaseCallbacks::TransactionMap& transactions);
132 
133   // ScriptWrappable
134   bool HasPendingActivity() const final;
135 
136   // ExecutionContextLifecycleObserver
137   void ContextDestroyed() override;
138 
139   // EventTarget
140   const AtomicString& InterfaceName() const override;
141   ExecutionContext* GetExecutionContext() const override;
142 
IsClosePending()143   bool IsClosePending() const { return close_pending_; }
144   void ForceClose();
Metadata()145   const IDBDatabaseMetadata& Metadata() const { return metadata_; }
146   void EnqueueEvent(Event*);
147 
148   int64_t FindObjectStoreId(const String& name) const;
ContainsObjectStore(const String & name)149   bool ContainsObjectStore(const String& name) const {
150     return FindObjectStoreId(name) != IDBObjectStoreMetadata::kInvalidId;
151   }
152   void RenameObjectStore(int64_t store_id, const String& new_name);
153   void RevertObjectStoreCreation(int64_t object_store_id);
154   void RevertObjectStoreMetadata(
155       scoped_refptr<IDBObjectStoreMetadata> old_metadata);
156 
157   // Will return nullptr if this database is stopped.
Backend()158   WebIDBDatabase* Backend() const { return backend_.get(); }
159 
160   static int64_t NextTransactionId();
161   static int32_t NextObserverId();
162 
163   static const char kCannotObserveVersionChangeTransaction[];
164   static const char kIndexDeletedErrorMessage[];
165   static const char kIndexNameTakenErrorMessage[];
166   static const char kIsKeyCursorErrorMessage[];
167   static const char kNoKeyOrKeyRangeErrorMessage[];
168   static const char kNoSuchIndexErrorMessage[];
169   static const char kNoSuchObjectStoreErrorMessage[];
170   static const char kNoValueErrorMessage[];
171   static const char kNotValidKeyErrorMessage[];
172   static const char kNotVersionChangeTransactionErrorMessage[];
173   static const char kObjectStoreDeletedErrorMessage[];
174   static const char kObjectStoreNameTakenErrorMessage[];
175   static const char kRequestNotFinishedErrorMessage[];
176   static const char kSourceDeletedErrorMessage[];
177   static const char kTransactionFinishedErrorMessage[];
178   static const char kTransactionInactiveErrorMessage[];
179   static const char kTransactionReadOnlyErrorMessage[];
180   static const char kDatabaseClosedErrorMessage[];
181 
182  protected:
183   // EventTarget
184   DispatchEventResult DispatchEventInternal(Event&) override;
185 
186  private:
187   IDBObjectStore* createObjectStore(const String& name,
188                                     const IDBKeyPath&,
189                                     bool auto_increment,
190                                     ExceptionState&);
191   void CloseConnection();
192 
193   IDBDatabaseMetadata metadata_;
194   std::unique_ptr<WebIDBDatabase> backend_;
195   Member<IDBTransaction> version_change_transaction_;
196   HeapHashMap<int64_t, Member<IDBTransaction>> transactions_;
197   HeapHashMap<int32_t, Member<IDBObserver>> observers_;
198   // No interface here, so no need to bind it.  This is only for
199   // lifetime observation of the use of IndexedDB from the browser.
200   mojo::PendingRemote<mojom::blink::ObservedFeature> connection_lifetime_;
201 
202   bool close_pending_ = false;
203 
204   Member<EventQueue> event_queue_;
205 
206   Member<IDBDatabaseCallbacks> database_callbacks_;
207   // Maintain the isolate so that all externally allocated memory can be
208   // registered against it.
209   v8::Isolate* isolate_;
210 
211   FrameOrWorkerScheduler::SchedulingAffectingFeatureHandle
212       feature_handle_for_scheduler_;
213 };
214 
215 }  // namespace blink
216 
217 #endif  // THIRD_PARTY_BLINK_RENDERER_MODULES_INDEXEDDB_IDB_DATABASE_H_
218