All files / near-membrane-node/src node-realm.ts

95.65% Statements 22/23
94.44% Branches 17/18
50% Functions 1/2
95.65% Lines 22/23

Press n or j to go to the next uncovered block, b, p or k for the previous block.

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79                                    4x   4x           24x 1x                 23x 23x 23x 4x 4x   23x 23x 23x                       23x     23x 23x 2x     23x             23x 15x 15x 15x   23x    
import {
    assignFilteredGlobalDescriptorsFromPropertyDescriptorMap,
    createBlueConnector,
    createRedConnector,
    getFilteredGlobalOwnKeys,
    linkIntrinsics,
    VirtualEnvironment,
} from '@locker/near-membrane-base';
import {
    ObjectAssign,
    toSafeWeakMap,
    TypeErrorCtor,
    WeakMapCtor,
} from '@locker/near-membrane-shared';
import type { Connector } from '@locker/near-membrane-base';
import { runInNewContext } from 'node:vm';
import type { NodeEnvironmentOptions } from './types';
 
const blueCreateHooksCallbackCache = toSafeWeakMap(new WeakMapCtor<typeof globalThis, Connector>());
 
let defaultGlobalOwnKeys: PropertyKey[] | null = null;
 
export default function createVirtualEnvironment(
    globalObject: typeof globalThis,
    providedOptions?: NodeEnvironmentOptions
): VirtualEnvironment {
    if (typeof globalObject !== 'object' || globalObject === null) {
        throw new TypeErrorCtor('Missing global object virtualization target.');
    }
    const {
        distortionCallback,
        endowments,
        globalObjectShape,
        instrumentation,
        liveTargetCallback,
        signSourceCallback,
    } = ObjectAssign({ __proto__: null }, providedOptions) as NodeEnvironmentOptions;
    let blueConnector = blueCreateHooksCallbackCache.get(globalObject) as Connector | undefined;
    if (blueConnector === undefined) {
        blueConnector = createBlueConnector(globalObject);
        blueCreateHooksCallbackCache.set(globalObject, blueConnector);
    }
    const redGlobalObject = runInNewContext('globalThis');
    const { eval: redIndirectEval } = redGlobalObject;
    const env = new VirtualEnvironment({
        blueConnector,
        redConnector: createRedConnector(
            signSourceCallback
                ? (sourceText: string) => redIndirectEval(signSourceCallback(sourceText))
                : redIndirectEval
        ),
        distortionCallback,
        instrumentation,
        liveTargetCallback,
        signSourceCallback,
    });
    linkIntrinsics(env, globalObject);
 
    const shouldUseDefaultGlobalOwnKeys =
        typeof globalObjectShape !== 'object' || globalObjectShape === null;
    if (shouldUseDefaultGlobalOwnKeys && defaultGlobalOwnKeys === null) {
        defaultGlobalOwnKeys = getFilteredGlobalOwnKeys(redGlobalObject);
    }
 
    env.lazyRemapProperties(
        globalObject,
        shouldUseDefaultGlobalOwnKeys
            ? (defaultGlobalOwnKeys as PropertyKey[])
            : getFilteredGlobalOwnKeys(globalObjectShape)
    );
 
    if (endowments) {
        const filteredEndowments = {};
        assignFilteredGlobalDescriptorsFromPropertyDescriptorMap(filteredEndowments, endowments);
        env.remapProperties(globalObject, filteredEndowments);
    }
    return env;
}