Después de cargar dinámicamente un módulo, es decir, después de que se haya resuelto la promesa correspondiente, se puede actuar con una función o expresión lambda en el resultado. Me sorprendió descubrir que la instancia del módulo (proporcionada por la promesa) no tiene un prototipo:
import("./module.js").then(x => { console.log(typeof x); // yields 'object' as expected console.log(x instanceof Object); // yields false !! console.log(x.__proto__); // yields undefined !! console.log(Object.getPrototypeOf(x)); // yields null !! // but one can certainly access exported variables / functions x.exportedFunction(); }) Aparentemente, a pesar de ser un 'objeto', x no parece ser una instancia de Object y no parece tener ningún prototipo. Yo no era consciente de que esto es incluso posible. Firefox/Chrome y Safari dieron el mismo resultado (el que deletreé en los comentarios del código). ¿Hay una explicación? ¿Está esto especificado en alguna parte? ¿Qué tipo de objeto es este módulo x ?
Nota : no estoy familiarizado con mecanografiado, por lo que no estoy seguro de si mi pregunta podría considerarse un duplicado de esta
Editar : Me acabo de dar cuenta de que uno obtiene el mismo pseudo-objeto extraño para módulos importados estáticamente en un espacio de nombres o un objeto de módulo a través import * as x from "./module.js" . Aunque MDN menciona estos objetos, no explica qué son.
Hay toda una gama de los llamados objetos exóticos , que se desvían de los objetos ordinarios . El tipo de una instancia de módulo ES6 importada es uno de estos, el objeto exótico del espacio de nombres del módulo :
Un objeto es un objeto exótico de espacio de nombres de módulo si es [[GetPrototypeOf]], [[SetPrototypeOf]], [[IsExtensible]], [[PreventExtensions]], [[GetOwnProperty]], [[DefineOwnProperty]], [[HasProperty] ], [[Get]], [[Set]], [[Delete]] y [[OwnPropertyKeys]] utilizan las definiciones de esta sección, y sus otros métodos internos esenciales utilizan las definiciones que se encuentran en 10.1. Estos métodos son instalados por ModuleNamespaceCreate.
¿Por qué x instanceof Object , x. __proto__ , Object. getPrototypeOf (x) se comporta tan raro? Veamos el método interno del objeto que está involucrado aquí:
ObtenerPrototipoDe
El método interno [[GetPrototypeOf]] de un objeto exótico de espacio de nombres de módulo no acepta argumentos y devuelve una finalización normal que contiene un valor nulo. Realiza los siguientes pasos cuando se le llama:
1. Return null.
¿Cómo se crean tales objetos? Hay un método especial para eso:
ModuleNamespaceCreate (módulo, exportaciones)
La operación abstracta ModuleNamespaceCreate toma el módulo de argumentos (un registro de módulo) y exporta (una lista de cadenas) y devuelve un objeto exótico de espacio de nombres de módulo. Se utiliza para especificar la creación de nuevos objetos exóticos de espacio de nombres de módulo. Realiza los siguientes pasos cuando se le llama:
1. Assert: module.[[Namespace]] is empty. 2. Let internalSlotsList be the internal slots listed in Table 35. 3. Let M be MakeBasicObject(internalSlotsList). 4. Set M's essential internal methods to the definitions specified in 10.4.6. 5. Set M.[[Module]] to module. 6. Let sortedExports be a List whose elements are the elements of exports ordered as if an Array of the same values had been sorted using %Array.prototype.sort% using undefined as comparefn. 7. Set M.[[Exports]] to sortedExports. 8. Create own properties of M corresponding to the definitions in 28.3. 9. Set module.[[Namespace]] to M. 10. Return M.