@@ -140,6 +140,8 @@ export class DataSchemaCompiler {
140140
141141 private readonly compiledScriptCache : LRUCache < string , vm . Script > ;
142142
143+ private compileV8ContextCache : vm . Context ;
144+
143145 // FIXME: Is public only because of tests, should be private
144146 public compilePromise : any ;
145147
@@ -172,6 +174,7 @@ export class DataSchemaCompiler {
172174 this . workerPool = null ;
173175 this . compilerId = options . compilerId || 'default' ;
174176 this . compiledScriptCache = options . compiledScriptCache ;
177+ this . compileV8ContextCache = vm . createContext ( { } ) ;
175178 }
176179
177180 public compileObjects ( compileServices , objects , errorsReport : ErrorReporter ) {
@@ -563,7 +566,18 @@ export class DataSchemaCompiler {
563566 return this . compiledScriptCache . get ( cacheKey ) ! ;
564567 }
565568
566- const script = new vm . Script ( file . content , { filename : file . fileName } ) ;
569+ // As we run all data model files in the same context,
570+ // we need to wrap the code in an IIFE to avoid polluting and modifying the global scope,
571+ // and to provide a controlled environment for the code execution.
572+ const wrappedCode = `
573+ (function(globals) {
574+ "use strict";
575+ const { view, cube, context, addExport, setExport, asyncModule, require, COMPILE_CONTEXT } = globals;
576+ ${ file . content }
577+ })(sandboxLocals);
578+ ` ;
579+
580+ const script = new vm . Script ( wrappedCode , { filename : file . fileName } ) ;
567581 this . compiledScriptCache . set ( cacheKey , script ) ;
568582 return script ;
569583 }
@@ -582,18 +596,17 @@ export class DataSchemaCompiler {
582596 try {
583597 const script = this . getJsScript ( file ) ;
584598
585- script . runInNewContext ( {
599+ const sandboxLocals = Object . freeze ( {
586600 view : ( name , cube ) => (
587601 ! cube ?
588602 this . cubeFactory ( { ...name , fileName : file . fileName , isView : true } ) :
589603 cubes . push ( { ...cube , name, fileName : file . fileName , isView : true } )
590604 ) ,
591- cube :
592- ( name , cube ) => (
593- ! cube ?
594- this . cubeFactory ( { ...name , fileName : file . fileName } ) :
595- cubes . push ( { ...cube , name, fileName : file . fileName } )
596- ) ,
605+ cube : ( name , cube ) => (
606+ ! cube ?
607+ this . cubeFactory ( { ...name , fileName : file . fileName } ) :
608+ cubes . push ( { ...cube , name, fileName : file . fileName } )
609+ ) ,
597610 context : ( name , context ) => contexts . push ( { ...context , name, fileName : file . fileName } ) ,
598611 addExport : ( obj ) => {
599612 exports [ file . fileName ] = exports [ file . fileName ] || { } ;
@@ -637,9 +650,15 @@ export class DataSchemaCompiler {
637650 }
638651 } ,
639652 COMPILE_CONTEXT : this . standalone ? this . standaloneCompileContextProxy ( ) : this . cloneCompileContextWithGetterAlias ( this . compileContext || { } ) ,
640- } , { filename : file . fileName , timeout : 15000 } ) ;
653+ } ) ;
654+
655+ this . compileV8ContextCache . sandboxLocals = sandboxLocals ;
656+
657+ script . runInContext ( this . compileV8ContextCache , { timeout : 15000 } ) ;
641658 } catch ( e ) {
642659 errorsReport . error ( e ) ;
660+ } finally {
661+ delete this . compileV8ContextCache . sandboxLocals ;
643662 }
644663 }
645664
0 commit comments