Most libraries don't work across frames due to each having its own copy of the host's constructors. This renders certain coding practices (relying on instanceof or constructor comparisons) unreliable.
See:
- mrdoob/three.js#5886
- http://perfectionkills.com/instanceof-considered-harmful-or-how-to-write-a-robust-isarray/
To work around the issue Atomic applies symbolic names to constructors. These same names can be applied to constructors in other frames. Doing this guarantees identical constructors (from different frames) share a common identity. This enables is and ako (while CROSSREALM=1) to unambiguously identify objects.
Third-party code including most polyfills (even natives) should be considered unreliable and so there is no consistent means by which developers have tackled cross-realm operability. Only fully-controlled code with no external dependencies (unknowns) can be trusted!
Set CROSSREALM=1 to compile cross-realm operable bundles and CROSSREALM=0 when not needed as this option is not cost free.
- Don't use
instanceof. Useako. - Don't check constructors. Use
is. - Don't bake environment globals (e.g.
document,location) into functions or, at least, provide an overload which allows defaults to be overridden. - Type checking functions (
isString(s),isElement(e), etc.) should be built fromisorako. - Export behaviors. Apply the behaviors and shared keys (e.g.
keying) across environments which share the library. - Unless frequently used, don't create type-testing functions such as
isThing(t). Preferis(obj, Thing).
Behaviors can be assigned to types if foreign hosts so they understand a module's protocols. Each module exports a behave function which imbues behavior to a select environment/window.
import * as _ from "atomic/core";
import * as dom from "atomic/dom";
_.behave(window); //includes all known types
_.behave({Array, Object}); //includes only specified types
dom.behave(window);
dom.behave({Window, Location, HTMLDocument});Behaviors (and names) are automatically imbued in the frame in which a module loads. It is only necessary to manually imbue behaviors into foreign frames which pass objects into the current.