1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #ifndef CONTENT_CHILD_INDEXED_DB_INDEXED_DB_DISPATCHER_H_
6 #define CONTENT_CHILD_INDEXED_DB_INDEXED_DB_DISPATCHER_H_
11 #include "base/gtest_prod_util.h"
12 #include "base/id_map.h"
13 #include "base/memory/ref_counted.h"
14 #include "base/strings/nullable_string16.h"
15 #include "content/common/content_export.h"
16 #include "ipc/ipc_sync_message_filter.h"
17 #include "third_party/WebKit/public/platform/WebIDBCallbacks.h"
18 #include "third_party/WebKit/public/platform/WebIDBCursor.h"
19 #include "third_party/WebKit/public/platform/WebIDBDatabase.h"
20 #include "third_party/WebKit/public/platform/WebIDBDatabaseCallbacks.h"
21 #include "webkit/child/worker_task_runner.h"
23 struct IndexedDBDatabaseMetadata;
24 struct IndexedDBMsg_CallbacksSuccessCursorContinue_Params;
25 struct IndexedDBMsg_CallbacksSuccessCursorPrefetch_Params;
26 struct IndexedDBMsg_CallbacksSuccessIDBCursor_Params;
27 struct IndexedDBMsg_CallbacksUpgradeNeeded_Params;
35 class IndexedDBKeyPath;
36 class IndexedDBKeyRange;
37 class WebIDBCursorImpl;
38 class WebIDBDatabaseImpl;
39 class ThreadSafeSender;
41 CONTENT_EXPORT extern const size_t kMaxIDBValueSizeInBytes;
43 // Handle the indexed db related communication for this context thread - the
44 // main thread and each worker thread have their own copies.
45 class CONTENT_EXPORT IndexedDBDispatcher
46 : public webkit_glue::WorkerTaskRunner::Observer {
48 // Constructor made public to allow RenderThreadImpl to own a copy without
49 // failing a NOTREACHED in ThreadSpecificInstance in tests that instantiate
50 // two copies of RenderThreadImpl on the same thread. Everyone else probably
51 // wants to use ThreadSpecificInstance().
52 explicit IndexedDBDispatcher(ThreadSafeSender* thread_safe_sender);
53 virtual ~IndexedDBDispatcher();
55 // |thread_safe_sender| needs to be passed in because if the call leads to
56 // construction it will be needed.
57 static IndexedDBDispatcher* ThreadSpecificInstance(
58 ThreadSafeSender* thread_safe_sender);
60 // webkit_glue::WorkerTaskRunner::Observer implementation.
61 virtual void OnWorkerRunLoopStopped() OVERRIDE;
63 static blink::WebIDBMetadata ConvertMetadata(
64 const IndexedDBDatabaseMetadata& idb_metadata);
66 void OnMessageReceived(const IPC::Message& msg);
68 // This method is virtual so it can be overridden in unit tests.
69 virtual bool Send(IPC::Message* msg);
71 void RequestIDBFactoryGetDatabaseNames(
72 blink::WebIDBCallbacks* callbacks,
73 const std::string& database_identifier);
75 void RequestIDBFactoryOpen(
76 const base::string16& name,
79 blink::WebIDBCallbacks* callbacks,
80 blink::WebIDBDatabaseCallbacks* database_callbacks,
81 const std::string& database_identifier);
83 void RequestIDBFactoryDeleteDatabase(const base::string16& name,
84 blink::WebIDBCallbacks* callbacks,
85 const std::string& database_identifier);
87 // This method is virtual so it can be overridden in unit tests.
88 virtual void RequestIDBCursorAdvance(unsigned long count,
89 blink::WebIDBCallbacks* callbacks_ptr,
91 int64 transaction_id);
93 // This method is virtual so it can be overridden in unit tests.
94 virtual void RequestIDBCursorContinue(const IndexedDBKey& key,
95 const IndexedDBKey& primary_key,
96 blink::WebIDBCallbacks* callbacks_ptr,
98 int64 transaction_id);
100 // This method is virtual so it can be overridden in unit tests.
101 virtual void RequestIDBCursorPrefetch(int n,
102 blink::WebIDBCallbacks* callbacks_ptr,
103 int32 ipc_cursor_id);
105 // This method is virtual so it can be overridden in unit tests.
106 virtual void RequestIDBCursorPrefetchReset(int used_prefetches,
107 int unused_prefetches,
108 int32 ipc_cursor_id);
110 void RequestIDBDatabaseClose(int32 ipc_database_id,
111 int32 ipc_database_callbacks_id);
113 void RequestIDBDatabaseCreateTransaction(
114 int32 ipc_database_id,
115 int64 transaction_id,
116 blink::WebIDBDatabaseCallbacks* database_callbacks_ptr,
117 blink::WebVector<long long> object_store_ids,
118 blink::WebIDBDatabase::TransactionMode mode);
120 void RequestIDBDatabaseGet(int32 ipc_database_id,
121 int64 transaction_id,
122 int64 object_store_id,
124 const IndexedDBKeyRange& key_range,
126 blink::WebIDBCallbacks* callbacks);
128 void RequestIDBDatabasePut(
129 int32 ipc_database_id,
130 int64 transaction_id,
131 int64 object_store_id,
132 const blink::WebData& value,
133 const IndexedDBKey& key,
134 blink::WebIDBDatabase::PutMode put_mode,
135 blink::WebIDBCallbacks* callbacks,
136 const blink::WebVector<long long>& index_ids,
137 const blink::WebVector<blink::WebVector<blink::WebIDBKey> >&
140 void RequestIDBDatabaseOpenCursor(int32 ipc_database_id,
141 int64 transaction_id,
142 int64 object_store_id,
144 const IndexedDBKeyRange& key_range,
145 blink::WebIDBCursor::Direction direction,
147 blink::WebIDBDatabase::TaskType task_type,
148 blink::WebIDBCallbacks* callbacks);
150 void RequestIDBDatabaseCount(int32 ipc_database_id,
151 int64 transaction_id,
152 int64 object_store_id,
154 const IndexedDBKeyRange& key_range,
155 blink::WebIDBCallbacks* callbacks);
157 void RequestIDBDatabaseDeleteRange(int32 ipc_database_id,
158 int64 transaction_id,
159 int64 object_store_id,
160 const IndexedDBKeyRange& key_range,
161 blink::WebIDBCallbacks* callbacks);
163 void RequestIDBDatabaseClear(int32 ipc_database_id,
164 int64 transaction_id,
165 int64 object_store_id,
166 blink::WebIDBCallbacks* callbacks);
168 virtual void CursorDestroyed(int32 ipc_cursor_id);
169 void DatabaseDestroyed(int32 ipc_database_id);
172 FRIEND_TEST_ALL_PREFIXES(IndexedDBDispatcherTest, CursorReset);
173 FRIEND_TEST_ALL_PREFIXES(IndexedDBDispatcherTest, CursorTransactionId);
174 FRIEND_TEST_ALL_PREFIXES(IndexedDBDispatcherTest, ValueSizeTest);
176 enum { kAllCursors = -1 };
178 static int32 CurrentWorkerId() {
179 return webkit_glue::WorkerTaskRunner::Instance()->CurrentWorkerId();
182 template <typename T>
183 void init_params(T& params, blink::WebIDBCallbacks* callbacks_ptr) {
184 scoped_ptr<blink::WebIDBCallbacks> callbacks(callbacks_ptr);
185 params.ipc_thread_id = CurrentWorkerId();
186 params.ipc_callbacks_id = pending_callbacks_.Add(callbacks.release());
189 // IDBCallback message handlers.
190 void OnSuccessIDBDatabase(int32 ipc_thread_id,
191 int32 ipc_callbacks_id,
192 int32 ipc_database_callbacks_id,
194 const IndexedDBDatabaseMetadata& idb_metadata);
195 void OnSuccessIndexedDBKey(int32 ipc_thread_id,
196 int32 ipc_callbacks_id,
197 const IndexedDBKey& key);
199 void OnSuccessOpenCursor(
200 const IndexedDBMsg_CallbacksSuccessIDBCursor_Params& p);
201 void OnSuccessCursorContinue(
202 const IndexedDBMsg_CallbacksSuccessCursorContinue_Params& p);
203 void OnSuccessCursorPrefetch(
204 const IndexedDBMsg_CallbacksSuccessCursorPrefetch_Params& p);
205 void OnSuccessStringList(int32 ipc_thread_id,
206 int32 ipc_callbacks_id,
207 const std::vector<base::string16>& value);
208 void OnSuccessValue(int32 ipc_thread_id,
209 int32 ipc_callbacks_id,
210 const std::string& value);
211 void OnSuccessValueWithKey(int32 ipc_thread_id,
212 int32 ipc_callbacks_id,
213 const std::string& value,
214 const IndexedDBKey& primary_key,
215 const IndexedDBKeyPath& key_path);
216 void OnSuccessInteger(int32 ipc_thread_id,
217 int32 ipc_callbacks_id,
219 void OnSuccessUndefined(int32 ipc_thread_id, int32 ipc_callbacks_id);
220 void OnError(int32 ipc_thread_id,
221 int32 ipc_callbacks_id,
223 const base::string16& message);
224 void OnIntBlocked(int32 ipc_thread_id,
225 int32 ipc_callbacks_id,
226 int64 existing_version);
227 void OnUpgradeNeeded(const IndexedDBMsg_CallbacksUpgradeNeeded_Params& p);
228 void OnAbort(int32 ipc_thread_id,
229 int32 ipc_database_id,
230 int64 transaction_id,
232 const base::string16& message);
233 void OnComplete(int32 ipc_thread_id,
234 int32 ipc_database_id,
235 int64 transaction_id);
236 void OnForcedClose(int32 ipc_thread_id, int32 ipc_database_id);
237 void OnIntVersionChange(int32 ipc_thread_id,
238 int32 ipc_database_id,
242 // Reset cursor prefetch caches for all cursors except exception_cursor_id.
243 void ResetCursorPrefetchCaches(int64 transaction_id,
244 int32 ipc_exception_cursor_id);
246 scoped_refptr<ThreadSafeSender> thread_safe_sender_;
248 // Careful! WebIDBCallbacks wraps non-threadsafe data types. It must be
249 // destroyed and used on the same thread it was created on.
250 IDMap<blink::WebIDBCallbacks, IDMapOwnPointer> pending_callbacks_;
251 IDMap<blink::WebIDBDatabaseCallbacks, IDMapOwnPointer>
252 pending_database_callbacks_;
254 // Maps the ipc_callback_id from an open cursor request to the request's
255 // transaction_id. Used to assign the transaction_id to the WebIDBCursorImpl
256 // when it is created.
257 std::map<int32, int64> cursor_transaction_ids_;
259 // Map from cursor id to WebIDBCursorImpl.
260 std::map<int32, WebIDBCursorImpl*> cursors_;
262 std::map<int32, WebIDBDatabaseImpl*> databases_;
264 DISALLOW_COPY_AND_ASSIGN(IndexedDBDispatcher);
267 } // namespace content
269 #endif // CONTENT_CHILD_INDEXED_DB_INDEXED_DB_DISPATCHER_H_