1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7 #ifndef mozilla_dom_serviceworkerevents_h__
8 #define mozilla_dom_serviceworkerevents_h__
10 #include "mozilla/Attributes.h"
11 #include "mozilla/dom/Event.h"
12 #include "mozilla/dom/ExtendableEventBinding.h"
13 #include "mozilla/dom/ExtendableMessageEventBinding.h"
14 #include "mozilla/dom/FetchEventBinding.h"
15 #include "mozilla/dom/File.h"
16 #include "mozilla/dom/Promise.h"
17 #include "mozilla/dom/Response.h"
18 #include "mozilla/dom/WorkerCommon.h"
20 #include "nsProxyRelease.h"
21 #include "nsContentUtils.h"
23 class nsIInterceptedChannel
;
25 namespace mozilla::dom
{
33 class ResponseOrPromise
;
35 class ServiceWorkerRegistrationInfo
;
37 // Defined in ServiceWorker.cpp
38 bool ServiceWorkerVisible(JSContext
* aCx
, JSObject
* aObj
);
40 class CancelChannelRunnable final
: public Runnable
{
41 nsMainThreadPtrHandle
<nsIInterceptedChannel
> mChannel
;
42 nsMainThreadPtrHandle
<ServiceWorkerRegistrationInfo
> mRegistration
;
43 const nsresult mStatus
;
46 CancelChannelRunnable(
47 nsMainThreadPtrHandle
<nsIInterceptedChannel
>& aChannel
,
48 nsMainThreadPtrHandle
<ServiceWorkerRegistrationInfo
>& aRegistration
,
51 NS_IMETHOD
Run() override
;
54 enum ExtendableEventResult
{ Rejected
= 0, Resolved
};
56 class ExtendableEventCallback
{
58 virtual void FinishedWithResult(ExtendableEventResult aResult
) = 0;
60 NS_INLINE_DECL_PURE_VIRTUAL_REFCOUNTING
63 class ExtendableEvent
: public Event
{
65 class ExtensionsHandler
{
66 friend class ExtendableEvent
;
69 virtual bool WaitOnPromise(Promise
& aPromise
) = 0;
71 NS_INLINE_DECL_PURE_VIRTUAL_REFCOUNTING
74 virtual ~ExtensionsHandler();
76 // Also returns false if the owning ExtendableEvent is destroyed.
77 bool GetDispatchFlag() const;
80 // Only the owning ExtendableEvent is allowed to set this data.
81 void SetExtendableEvent(const ExtendableEvent
* const aExtendableEvent
);
83 MOZ_NON_OWNING_REF
const ExtendableEvent
* mExtendableEvent
= nullptr;
87 RefPtr
<ExtensionsHandler
> mExtensionsHandler
;
90 bool GetDispatchFlag() const { return mEvent
->mFlags
.mIsBeingDispatched
; }
92 bool WaitOnPromise(Promise
& aPromise
);
94 explicit ExtendableEvent(mozilla::dom::EventTarget
* aOwner
);
97 if (mExtensionsHandler
) {
98 mExtensionsHandler
->SetExtendableEvent(nullptr);
103 NS_DECL_ISUPPORTS_INHERITED
105 void SetKeepAliveHandler(ExtensionsHandler
* aExtensionsHandler
);
107 virtual JSObject
* WrapObjectInternal(
108 JSContext
* aCx
, JS::Handle
<JSObject
*> aGivenProto
) override
{
109 return mozilla::dom::ExtendableEvent_Binding::Wrap(aCx
, this, aGivenProto
);
112 static already_AddRefed
<ExtendableEvent
> Constructor(
113 mozilla::dom::EventTarget
* aOwner
, const nsAString
& aType
,
114 const EventInit
& aOptions
) {
115 RefPtr
<ExtendableEvent
> e
= new ExtendableEvent(aOwner
);
116 bool trusted
= e
->Init(aOwner
);
117 e
->InitEvent(aType
, aOptions
.mBubbles
, aOptions
.mCancelable
);
118 e
->SetTrusted(trusted
);
119 e
->SetComposed(aOptions
.mComposed
);
123 static already_AddRefed
<ExtendableEvent
> Constructor(
124 const GlobalObject
& aGlobal
, const nsAString
& aType
,
125 const EventInit
& aOptions
) {
126 nsCOMPtr
<EventTarget
> target
= do_QueryInterface(aGlobal
.GetAsSupports());
127 return Constructor(target
, aType
, aOptions
);
130 void WaitUntil(JSContext
* aCx
, Promise
& aPromise
, ErrorResult
& aRv
);
132 virtual ExtendableEvent
* AsExtendableEvent() override
{ return this; }
135 class FetchEvent final
: public ExtendableEvent
{
136 RefPtr
<FetchEventOp
> mRespondWithHandler
;
137 nsMainThreadPtrHandle
<nsIInterceptedChannel
> mChannel
;
138 nsMainThreadPtrHandle
<ServiceWorkerRegistrationInfo
> mRegistration
;
139 RefPtr
<Request
> mRequest
;
140 RefPtr
<Promise
> mHandled
;
141 RefPtr
<Promise
> mPreloadResponse
;
142 nsCString mScriptSpec
;
143 nsCString mPreventDefaultScriptSpec
;
145 nsString mResultingClientId
;
146 uint32_t mPreventDefaultLineNumber
;
147 uint32_t mPreventDefaultColumnNumber
;
151 explicit FetchEvent(EventTarget
* aOwner
);
155 NS_DECL_ISUPPORTS_INHERITED
156 NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(FetchEvent
, ExtendableEvent
)
158 virtual JSObject
* WrapObjectInternal(
159 JSContext
* aCx
, JS::Handle
<JSObject
*> aGivenProto
) override
{
160 return FetchEvent_Binding::Wrap(aCx
, this, aGivenProto
);
164 nsMainThreadPtrHandle
<nsIInterceptedChannel
>& aChannel
,
165 nsMainThreadPtrHandle
<ServiceWorkerRegistrationInfo
>& aRegistration
,
166 const nsACString
& aScriptSpec
);
168 void PostInit(const nsACString
& aScriptSpec
,
169 RefPtr
<FetchEventOp
> aRespondWithHandler
);
171 static already_AddRefed
<FetchEvent
> Constructor(
172 const GlobalObject
& aGlobal
, const nsAString
& aType
,
173 const FetchEventInit
& aOptions
);
175 bool WaitToRespond() const { return mWaitToRespond
; }
177 Request
* Request_() const {
178 MOZ_ASSERT(mRequest
);
182 void GetClientId(nsAString
& aClientId
) const { aClientId
= mClientId
; }
184 void GetResultingClientId(nsAString
& aResultingClientId
) const {
185 aResultingClientId
= mResultingClientId
;
188 Promise
* Handled() const { return mHandled
; }
190 Promise
* PreloadResponse() const { return mPreloadResponse
; }
192 void RespondWith(JSContext
* aCx
, Promise
& aArg
, ErrorResult
& aRv
);
194 // Pull in the Event version of PreventDefault so we don't get
195 // shadowing warnings.
196 using Event::PreventDefault
;
197 void PreventDefault(JSContext
* aCx
, CallerType aCallerType
) override
;
199 void ReportCanceled();
202 class PushMessageData final
: public nsISupports
, public nsWrapperCache
{
204 NS_DECL_CYCLE_COLLECTING_ISUPPORTS
205 NS_DECL_CYCLE_COLLECTION_WRAPPERCACHE_CLASS(PushMessageData
)
207 virtual JSObject
* WrapObject(JSContext
* aCx
,
208 JS::Handle
<JSObject
*> aGivenProto
) override
;
210 nsIGlobalObject
* GetParentObject() const { return mOwner
; }
212 void Json(JSContext
* cx
, JS::MutableHandle
<JS::Value
> aRetval
,
214 void Text(nsAString
& aData
);
215 void ArrayBuffer(JSContext
* cx
, JS::MutableHandle
<JSObject
*> aRetval
,
217 already_AddRefed
<mozilla::dom::Blob
> Blob(ErrorResult
& aRv
);
219 PushMessageData(nsIGlobalObject
* aOwner
, nsTArray
<uint8_t>&& aBytes
);
222 nsCOMPtr
<nsIGlobalObject
> mOwner
;
223 nsTArray
<uint8_t> mBytes
;
224 nsString mDecodedText
;
227 nsresult
EnsureDecodedText();
228 uint8_t* GetContentsCopy();
231 class PushEvent final
: public ExtendableEvent
{
232 RefPtr
<PushMessageData
> mData
;
235 explicit PushEvent(mozilla::dom::EventTarget
* aOwner
);
236 ~PushEvent() = default;
239 NS_DECL_ISUPPORTS_INHERITED
240 NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(PushEvent
, ExtendableEvent
)
242 virtual JSObject
* WrapObjectInternal(
243 JSContext
* aCx
, JS::Handle
<JSObject
*> aGivenProto
) override
;
245 static already_AddRefed
<PushEvent
> Constructor(
246 mozilla::dom::EventTarget
* aOwner
, const nsAString
& aType
,
247 const PushEventInit
& aOptions
, ErrorResult
& aRv
);
249 static already_AddRefed
<PushEvent
> Constructor(const GlobalObject
& aGlobal
,
250 const nsAString
& aType
,
251 const PushEventInit
& aOptions
,
253 nsCOMPtr
<EventTarget
> owner
= do_QueryInterface(aGlobal
.GetAsSupports());
254 return Constructor(owner
, aType
, aOptions
, aRv
);
257 PushMessageData
* GetData() const { return mData
; }
260 class ExtendableMessageEvent final
: public ExtendableEvent
{
261 JS::Heap
<JS::Value
> mData
;
263 nsString mLastEventId
;
264 RefPtr
<Client
> mClient
;
265 RefPtr
<ServiceWorker
> mServiceWorker
;
266 RefPtr
<MessagePort
> mMessagePort
;
267 nsTArray
<RefPtr
<MessagePort
>> mPorts
;
270 explicit ExtendableMessageEvent(EventTarget
* aOwner
);
271 ~ExtendableMessageEvent();
274 NS_DECL_ISUPPORTS_INHERITED
275 NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS_INHERITED(ExtendableMessageEvent
,
278 virtual JSObject
* WrapObjectInternal(
279 JSContext
* aCx
, JS::Handle
<JSObject
*> aGivenProto
) override
{
280 return mozilla::dom::ExtendableMessageEvent_Binding::Wrap(aCx
, this,
284 static already_AddRefed
<ExtendableMessageEvent
> Constructor(
285 mozilla::dom::EventTarget
* aOwner
, const nsAString
& aType
,
286 const ExtendableMessageEventInit
& aOptions
);
288 static already_AddRefed
<ExtendableMessageEvent
> Constructor(
289 const GlobalObject
& aGlobal
, const nsAString
& aType
,
290 const ExtendableMessageEventInit
& aOptions
);
292 void GetData(JSContext
* aCx
, JS::MutableHandle
<JS::Value
> aData
,
296 Nullable
<OwningClientOrServiceWorkerOrMessagePort
>& aValue
) const;
298 void GetOrigin(nsAString
& aOrigin
) const { aOrigin
= mOrigin
; }
300 void GetLastEventId(nsAString
& aLastEventId
) const {
301 aLastEventId
= mLastEventId
;
304 void GetPorts(nsTArray
<RefPtr
<MessagePort
>>& aPorts
);
307 } // namespace mozilla::dom
309 #endif /* mozilla_dom_serviceworkerevents_h__ */