Bug 1682632 - part2.4: ExtensionPort. r=baku

The ExtensionPort represents the webidl definitions of the runtime.Port WebExtensions API object.

A webidl dictionary will represent the serializable definition of the port properties, sent from
the API request handler to provide all the internal properties needed to create an instance
of the ExtensionPort webidl interface on the worker thread (which will be returned to the
extension code as the return value of the runtime.connect/connectNative methods and as a
parameter of the calls to the runtime.onConnect API event listeners).

Depends on D84684

Differential Revision: https://phabricator.services.mozilla.com/D84685
This commit is contained in:
Luca Greco 2021-06-09 19:20:43 +00:00
Родитель 1fe5785725
Коммит 27acdbe87d
6 изменённых файлов: 227 добавлений и 0 удалений

Просмотреть файл

@ -1582,6 +1582,11 @@ DOMInterfaces = {
'nativeType': 'mozilla::extensions::ExtensionEventManager',
},
'ExtensionPort': {
'headerFile': 'mozilla/extensions/ExtensionPort.h',
'nativeType': 'mozilla::extensions::ExtensionPort',
},
####################################
# Test Interfaces of various sorts #
####################################

Просмотреть файл

@ -0,0 +1,39 @@
/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/.
*
* This IDL file is related to the WebExtensions browser.runtime's Port.
*
* You are granted a license to use, reproduce and create derivative works of
* this document.
*/
[Exposed=(ServiceWorker), LegacyNoInterfaceObject]
interface ExtensionPort {
[Replaceable]
readonly attribute DOMString name;
[Replaceable]
readonly attribute object sender;
[Replaceable]
readonly attribute object? error;
[Throws, WebExtensionStub="NoReturn"]
void disconnect();
[Throws, WebExtensionStub="NoReturn"]
void postMessage(any message);
[Replaceable, SameObject]
readonly attribute ExtensionEventManager onDisconnect;
[Replaceable, SameObject]
readonly attribute ExtensionEventManager onMessage;
};
// Dictionary used by ExtensionAPIRequestForwarder and ExtensionCallabck to receive from the
// mozIExtensionAPIRequestHandler an internal description of a runtime.Port (and then used in
// the webidl implementation to create an ExtensionPort instance).
[GenerateInit]
dictionary ExtensionPortDescriptor {
required DOMString portId;
DOMString name = "";
};

Просмотреть файл

@ -1054,6 +1054,7 @@ WEBIDL_FILES += [
WEBIDL_FILES += [
"ExtensionBrowser.webidl",
"ExtensionEventManager.webidl",
"ExtensionPort.webidl",
]
# We only expose our prefable test interfaces in debug builds, just to be on

Просмотреть файл

@ -0,0 +1,89 @@
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "ExtensionPort.h"
#include "ExtensionEventManager.h"
#include "mozilla/dom/BindingUtils.h" // SequenceRooter
#include "mozilla/dom/ExtensionPortBinding.h"
#include "mozilla/dom/ScriptSettings.h" // AutoEntryScript
#include "nsIGlobalObject.h"
namespace mozilla {
namespace extensions {
NS_IMPL_CYCLE_COLLECTING_ADDREF(ExtensionPort);
NS_IMPL_CYCLE_COLLECTING_RELEASE(ExtensionPort)
NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE(ExtensionPort, mGlobal,
mOnDisconnectEventMgr,
mOnMessageEventMgr);
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(ExtensionPort)
NS_WRAPPERCACHE_INTERFACE_MAP_ENTRY
NS_INTERFACE_MAP_ENTRY(nsISupports)
NS_INTERFACE_MAP_END
// static
already_AddRefed<ExtensionPort> ExtensionPort::Create(
nsIGlobalObject* aGlobal, JS::Handle<JS::Value> aDescriptorValue,
ErrorResult& aRv) {
if (!aDescriptorValue.isObject()) {
aRv.Throw(NS_ERROR_UNEXPECTED);
return nullptr;
}
dom::AutoEntryScript aes(&aDescriptorValue.toObject(), __func__);
JSContext* acx = aes.cx();
auto portDescriptor = MakeUnique<dom::ExtensionPortDescriptor>();
if (!portDescriptor->Init(acx, aDescriptorValue, __func__)) {
aRv.Throw(NS_ERROR_UNEXPECTED);
return nullptr;
}
RefPtr<ExtensionPort> port =
new ExtensionPort(aGlobal, std::move(portDescriptor));
return port.forget();
}
ExtensionPort::ExtensionPort(
nsIGlobalObject* aGlobal,
UniquePtr<dom::ExtensionPortDescriptor> aPortDescriptor)
: mGlobal(aGlobal), mPortDescriptor(std::move(aPortDescriptor)) {
MOZ_DIAGNOSTIC_ASSERT(mGlobal);
}
nsString ExtensionPort::GetAPIObjectId() const {
return mPortDescriptor->mPortId;
}
JSObject* ExtensionPort::WrapObject(JSContext* aCx,
JS::Handle<JSObject*> aGivenProto) {
return dom::ExtensionPort_Binding::Wrap(aCx, this, aGivenProto);
}
nsIGlobalObject* ExtensionPort::GetParentObject() const { return mGlobal; }
ExtensionEventManager* ExtensionPort::OnMessage() {
if (!mOnMessageEventMgr) {
mOnMessageEventMgr = CreateEventManager(u"onMessage"_ns);
}
return mOnMessageEventMgr;
}
ExtensionEventManager* ExtensionPort::OnDisconnect() {
if (!mOnDisconnectEventMgr) {
mOnDisconnectEventMgr = CreateEventManager(u"onDisconnect"_ns);
}
return mOnDisconnectEventMgr;
}
void ExtensionPort::GetName(nsAString& aString) {
aString.Assign(mPortDescriptor->mName);
}
} // namespace extensions
} // namespace mozilla

Просмотреть файл

@ -0,0 +1,87 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set ts=8 sts=2 et sw=2 tw=80: */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#ifndef mozilla_extensions_ExtensionPort_h
#define mozilla_extensions_ExtensionPort_h
#include "js/TypeDecls.h"
#include "mozilla/dom/BindingDeclarations.h"
#include "nsWrapperCache.h"
#include "ExtensionAPIBase.h"
class nsIGlobalObject;
namespace mozilla {
class ErrorResult;
namespace dom {
struct ExtensionPortDescriptor;
}
namespace extensions {
class ExtensionEventManager;
class ExtensionPort final : public nsISupports,
public nsWrapperCache,
public ExtensionAPIBase {
nsCOMPtr<nsIGlobalObject> mGlobal;
RefPtr<ExtensionEventManager> mOnDisconnectEventMgr;
RefPtr<ExtensionEventManager> mOnMessageEventMgr;
UniquePtr<dom::ExtensionPortDescriptor> mPortDescriptor;
~ExtensionPort() = default;
ExtensionPort(nsIGlobalObject* aGlobal,
UniquePtr<dom::ExtensionPortDescriptor> aPortDescriptor);
protected:
// ExtensionAPIBase methods
nsIGlobalObject* GetGlobalObject() const override { return mGlobal; }
nsString GetAPINamespace() const override { return u"runtime"_ns; }
nsString GetAPIObjectType() const override { return u"Port"_ns; }
nsString GetAPIObjectId() const override;
public:
static already_AddRefed<ExtensionPort> Create(
nsIGlobalObject* aGlobal, JS::Handle<JS::Value> aDescriptorValue,
ErrorResult& aRv);
// nsWrapperCache interface methods
JSObject* WrapObject(JSContext* aCx,
JS::Handle<JSObject*> aGivenProto) override;
nsIGlobalObject* GetParentObject() const;
ExtensionEventManager* OnDisconnect();
ExtensionEventManager* OnMessage();
void GetName(nsAString& aString);
void GetError(JSContext* aCx, JS::MutableHandle<JSObject*> aResult) {
// TODO: this is currently just a placeholder, should be filled in
// with the actual implementation (which may send to the API request
// handler an API request to get the property value from the port object
// representation that lives on the main thread).
}
void GetSender(JSContext* aCx, JS::MutableHandle<JSObject*> aResult) {
// TODO: this is currently just a placeholder, needed to please the
// webidl binding which excepts this property to always return
// an object.
aResult.set(JS_NewPlainObject(aCx));
};
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS(ExtensionPort)
};
} // namespace extensions
} // namespace mozilla
#endif // mozilla_extensions_ExtensionPort_h

Просмотреть файл

@ -14,14 +14,20 @@ UNIFIED_SOURCES += [
"ExtensionBrowser.cpp",
"ExtensionEventListener.cpp",
"ExtensionEventManager.cpp",
"ExtensionPort.cpp",
]
EXPORTS.mozilla.extensions += [
"ExtensionAPIBase.h",
"ExtensionBrowser.h",
"ExtensionEventManager.h",
"ExtensionPort.h",
]
include("/ipc/chromium/chromium-config.mozbuild")
LOCAL_INCLUDES += [
"/js/xpconnect/src",
]
FINAL_LIBRARY = "xul"