|
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 * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of |
|
14 * its contributors may be used to endorse or promote products derived |
|
15 * from this software without specific prior written permission. |
|
16 * |
|
17 * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY |
|
18 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
|
19 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |
|
20 * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY |
|
21 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |
|
22 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |
|
23 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND |
|
24 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
|
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF |
|
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
|
27 */ |
|
28 |
|
29 #include "config.h" |
|
30 #include "IDBRequest.h" |
|
31 |
|
32 #if ENABLE(INDEXED_DATABASE) |
|
33 |
|
34 #include "Event.h" |
|
35 #include "EventException.h" |
|
36 #include "EventListener.h" |
|
37 #include "EventNames.h" |
|
38 #include "IDBDatabaseRequest.h" |
|
39 #include "IDBIndexRequest.h" |
|
40 #include "IDBErrorEvent.h" |
|
41 #include "IDBObjectStoreRequest.h" |
|
42 #include "IDBSuccessEvent.h" |
|
43 #include "ScriptExecutionContext.h" |
|
44 |
|
45 namespace WebCore { |
|
46 |
|
47 IDBRequest::IDBRequest(ScriptExecutionContext* context, PassRefPtr<IDBAny> source) |
|
48 : ActiveDOMObject(context, this) |
|
49 , m_source(source) |
|
50 , m_result(IDBAny::create()) |
|
51 , m_timer(this, &IDBRequest::timerFired) |
|
52 , m_stopped(false) |
|
53 , m_aborted(false) |
|
54 , m_readyState(INITIAL) |
|
55 { |
|
56 } |
|
57 |
|
58 IDBRequest::~IDBRequest() |
|
59 { |
|
60 if (m_readyState != DONE) |
|
61 abort(); |
|
62 } |
|
63 |
|
64 void IDBRequest::onError(PassRefPtr<IDBDatabaseError> error) |
|
65 { |
|
66 onEventCommon(); |
|
67 m_error = error; |
|
68 } |
|
69 |
|
70 void IDBRequest::onSuccess() |
|
71 { |
|
72 onEventCommon(); |
|
73 m_result->set(); |
|
74 } |
|
75 |
|
76 void IDBRequest::onSuccess(PassRefPtr<IDBDatabase> idbDatabase) |
|
77 { |
|
78 onEventCommon(); |
|
79 m_result->set(IDBDatabaseRequest::create(idbDatabase)); |
|
80 } |
|
81 |
|
82 void IDBRequest::onSuccess(PassRefPtr<IDBIndex> idbIndex) |
|
83 { |
|
84 onEventCommon(); |
|
85 m_result->set(IDBIndexRequest::create(idbIndex)); |
|
86 } |
|
87 |
|
88 void IDBRequest::onSuccess(PassRefPtr<IDBKey> idbKey) |
|
89 { |
|
90 onEventCommon(); |
|
91 m_result->set(idbKey); |
|
92 } |
|
93 |
|
94 void IDBRequest::onSuccess(PassRefPtr<IDBObjectStore> idbObjectStore) |
|
95 { |
|
96 onEventCommon(); |
|
97 m_result->set(IDBObjectStoreRequest::create(idbObjectStore)); |
|
98 } |
|
99 |
|
100 void IDBRequest::onSuccess(PassRefPtr<SerializedScriptValue> serializedScriptValue) |
|
101 { |
|
102 onEventCommon(); |
|
103 m_result->set(serializedScriptValue); |
|
104 } |
|
105 |
|
106 void IDBRequest::abort() |
|
107 { |
|
108 m_timer.stop(); |
|
109 m_aborted = true; |
|
110 // FIXME: This should cancel any pending work being done in the backend. |
|
111 } |
|
112 |
|
113 ScriptExecutionContext* IDBRequest::scriptExecutionContext() const |
|
114 { |
|
115 return ActiveDOMObject::scriptExecutionContext(); |
|
116 } |
|
117 |
|
118 void IDBRequest::stop() |
|
119 { |
|
120 abort(); |
|
121 m_selfRef = 0; // Could trigger a delete. |
|
122 } |
|
123 |
|
124 void IDBRequest::suspend() |
|
125 { |
|
126 m_timer.stop(); |
|
127 m_stopped = true; |
|
128 } |
|
129 |
|
130 void IDBRequest::resume() |
|
131 { |
|
132 m_stopped = false; |
|
133 // We only hold our self ref when we're waiting to dispatch an event. |
|
134 if (m_selfRef && !m_aborted) |
|
135 m_timer.startOneShot(0); |
|
136 } |
|
137 |
|
138 EventTargetData* IDBRequest::eventTargetData() |
|
139 { |
|
140 return &m_eventTargetData; |
|
141 } |
|
142 |
|
143 EventTargetData* IDBRequest::ensureEventTargetData() |
|
144 { |
|
145 return &m_eventTargetData; |
|
146 } |
|
147 |
|
148 void IDBRequest::timerFired(Timer<IDBRequest>*) |
|
149 { |
|
150 ASSERT(m_readyState == DONE); |
|
151 ASSERT(m_selfRef); |
|
152 ASSERT(!m_stopped); |
|
153 ASSERT(!m_aborted); |
|
154 |
|
155 // We need to keep self-referencing ourself, otherwise it's possible we'll be deleted. |
|
156 // But in some cases, suspend() could be called while we're dispatching an event, so we |
|
157 // need to make sure that resume() doesn't re-start the timer based on m_selfRef being set. |
|
158 RefPtr<IDBRequest> selfRef = m_selfRef.release(); |
|
159 |
|
160 if (m_error) { |
|
161 ASSERT(m_result->type() == IDBAny::UndefinedType); |
|
162 dispatchEvent(IDBErrorEvent::create(m_source, *m_error)); |
|
163 } else { |
|
164 ASSERT(m_result->type() != IDBAny::UndefinedType); |
|
165 dispatchEvent(IDBSuccessEvent::create(m_source, m_result)); |
|
166 } |
|
167 } |
|
168 |
|
169 void IDBRequest::onEventCommon() |
|
170 { |
|
171 ASSERT(m_readyState < DONE); |
|
172 ASSERT(m_result->type() == IDBAny::UndefinedType); |
|
173 ASSERT(!m_error); |
|
174 ASSERT(!m_selfRef); |
|
175 ASSERT(!m_timer.isActive()); |
|
176 |
|
177 if (m_aborted) |
|
178 return; |
|
179 |
|
180 m_readyState = DONE; |
|
181 m_selfRef = this; |
|
182 if (!m_stopped) |
|
183 m_timer.startOneShot(0); |
|
184 } |
|
185 |
|
186 } // namespace WebCore |
|
187 |
|
188 #endif |