descriptor-mixin.js (2710B)
1 /* This Source Code Form is subject to the terms of the Mozilla Public 2 * License, v. 2.0. If a copy of the MPL was not distributed with this 3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 4 5 "use strict"; 6 7 /** 8 * A Descriptor represents a debuggable context. It can be a browser tab, a tab on 9 * a remote device, like a tab on Firefox for Android. But it can also be an add-on, 10 * as well as firefox parent process, or just one of its content process. 11 * It can be very similar to a Target. The key difference is the lifecycle of these two classes. 12 * The descriptor is meant to be always alive and meaningful/usable until the end of the RDP connection. 13 * Typically a Tab Descriptor will describe the tab and not the one document currently loaded in this tab, 14 * while the Target, will describe this one document and a new Target may be created on each navigation. 15 */ 16 function DescriptorMixin(parentClass) { 17 class Descriptor extends parentClass { 18 constructor(client, targetFront, parentFront) { 19 super(client, targetFront, parentFront); 20 21 this._client = client; 22 23 // Pass a true value in order to distinguish this event reception 24 // from any manual destroy caused by the frontend 25 this.on( 26 "descriptor-destroyed", 27 this.destroy.bind(this, { isServerDestroyEvent: true }) 28 ); 29 } 30 31 get client() { 32 return this._client; 33 } 34 35 async destroy({ isServerDestroyEvent } = {}) { 36 if (this.isDestroyed()) { 37 return; 38 } 39 // This workaround is mostly done for Workers, as WorkerDescriptor 40 // extends the Target class, which causes some issue down the road: 41 // In Target.destroy, we call WorkerDescriptorActor.detach *before* calling super.destroy(), 42 // and so hold on before calling Front.destroy() which would reject all pending requests, including detach(). 43 // When calling detach, the server will emit "descriptor-destroyed", which will call Target.destroy again, 44 // but will still be blocked on detach resolution and won't call Front.destroy, and won't reject pending requests either. 45 // 46 // So call Front.baseFrontClassDestroyed manually from here, so that we ensure rejecting the pending detach request 47 // and unblock Target.destroy resolution. 48 // 49 // Here is the inheritance chain for WorkerDescriptor: 50 // WorkerDescriptor -> Descriptor (from descriptor-mixin.js) -> Target (from target-mixin.js) -> Front (protocol.js) -> Pool (protocol.js) -> EventEmitter 51 if (isServerDestroyEvent) { 52 this.baseFrontClassDestroy(); 53 } 54 55 await super.destroy(); 56 } 57 } 58 return Descriptor; 59 } 60 exports.DescriptorMixin = DescriptorMixin;