@@ -26,10 +26,23 @@ module.exports = function (bridge, glob) {
2626    // @note  we use a common scope for all executions. this causes issues when scripts are run inside the sandbox 
2727    // in parallel, but we still use this way for the legacy "persistent" behaviour needed in environment 
2828    const  scope  =  Scope . create ( { 
29-         eval : true , 
30-         ignore : [ 'require' ] , 
31-         block : [ 'bridge' ] 
32-     } ) ; 
29+             eval : true , 
30+             ignore : [ 'require' ] , 
31+             block : [ 'bridge' ] 
32+         } ) , 
33+         originalBridgeDispatch  =  bridge . dispatch ; 
34+ 
35+     bridge . dispatch  =  function  ( execution ,  ...args )  { 
36+         // What is the purpose of overriding the dispatch method here? 
37+         // When the user invokes pm.execution.skipRequest(), our goal is to halt the current request's execution. 
38+         // Since we lack a foolproof method to completely halt the script's execution, our approach is to 
39+         // cease sending events to the bridge, creating the appearance that the script ahead never ran. 
40+         if  ( execution  &&  execution . shouldSkipExecution )  { 
41+             return ; 
42+         } 
43+ 
44+         return  originalBridgeDispatch . call ( bridge ,  ...args ) ; 
45+     } ; 
3346
3447    // For caching required information provided during 
3548    // initialization which will be used during execution 
@@ -49,7 +62,7 @@ module.exports = function (bridge, glob) {
4962        if  ( ! template )  { 
5063            chai . use ( require ( 'chai-postman' ) ( sdk ,  _ ,  Ajv ) ) ; 
5164
52-             return  bridge . dispatch ( 'initialize' ) ; 
65+             return  bridge . dispatch ( null ,   'initialize' ) ; 
5366        } 
5467
5568        const  _module  =  {  exports : { }  } , 
@@ -66,7 +79,7 @@ module.exports = function (bridge, glob) {
6679
6780        scope . exec ( template ,  ( err )  =>  { 
6881            if  ( err )  { 
69-                 return  bridge . dispatch ( 'initialize' ,  err ) ; 
82+                 return  bridge . dispatch ( null ,   'initialize' ,  err ) ; 
7083            } 
7184
7285            const  {  chaiPlugin,  initializeExecution : setupExecution  }  =  ( _module  &&  _module . exports )  ||  { } ; 
@@ -79,7 +92,7 @@ module.exports = function (bridge, glob) {
7992                initializeExecution  =  setupExecution ; 
8093            } 
8194
82-             bridge . dispatch ( 'initialize' ) ; 
95+             bridge . dispatch ( null ,   'initialize' ) ; 
8396        } ) ; 
8497    } ) ; 
8598
@@ -97,7 +110,8 @@ module.exports = function (bridge, glob) {
97110     */ 
98111    bridge . on ( 'execute' ,  function  ( id ,  event ,  context ,  options )  { 
99112        if  ( ! ( id  &&  _ . isString ( id ) ) )  { 
100-             return  bridge . dispatch ( 'error' ,  new  Error ( 'sandbox: execution identifier parameter(s) missing' ) ) ; 
113+             return  bridge . dispatch ( null ,  'error' , 
114+                 new  Error ( 'sandbox: execution identifier parameter(s) missing' ) ) ; 
101115        } 
102116
103117        ! options  &&  ( options  =  { } ) ; 
@@ -136,8 +150,8 @@ module.exports = function (bridge, glob) {
136150                // For compatibility, dispatch the single assertion as an array. 
137151                ! Array . isArray ( assertions )  &&  ( assertions  =  [ assertions ] ) ; 
138152
139-                 bridge . dispatch ( assertionEventName ,  options . cursor ,  assertions ) ; 
140-                 bridge . dispatch ( EXECUTION_ASSERTION_EVENT ,  options . cursor ,  assertions ) ; 
153+                 bridge . dispatch ( execution ,   assertionEventName ,  options . cursor ,  assertions ) ; 
154+                 bridge . dispatch ( execution ,   EXECUTION_ASSERTION_EVENT ,  options . cursor ,  assertions ) ; 
141155            } ; 
142156
143157        let  waiting , 
@@ -148,8 +162,8 @@ module.exports = function (bridge, glob) {
148162        // create the controlled timers 
149163        timers  =  new  PostmanTimers ( null ,  function  ( err )  { 
150164            if  ( err )  {  // propagate the error out of sandbox 
151-                 bridge . dispatch ( errorEventName ,  options . cursor ,  err ) ; 
152-                 bridge . dispatch ( EXECUTION_ERROR_EVENT ,  options . cursor ,  err ) ; 
165+                 bridge . dispatch ( execution ,   errorEventName ,  options . cursor ,  err ) ; 
166+                 bridge . dispatch ( execution ,   EXECUTION_ERROR_EVENT ,  options . cursor ,  err ) ; 
153167            } 
154168        } ,  function  ( )  { 
155169            execution . return . async  =  true ; 
@@ -169,16 +183,22 @@ module.exports = function (bridge, glob) {
169183            bridge . off ( cookiesEventName ) ; 
170184
171185            if  ( err )  {  // fire extra execution error event 
172-                 bridge . dispatch ( errorEventName ,  options . cursor ,  err ) ; 
173-                 bridge . dispatch ( EXECUTION_ERROR_EVENT ,  options . cursor ,  err ) ; 
186+                 bridge . dispatch ( null ,   errorEventName ,  options . cursor ,  err ) ; 
187+                 bridge . dispatch ( null ,   EXECUTION_ERROR_EVENT ,  options . cursor ,  err ) ; 
174188            } 
175189
176190            // @note  delete response from the execution object to avoid dispatching 
177191            // the large response payload back due to performance reasons. 
178192            execution . response  &&  ( delete  execution . response ) ; 
179193
180194            // fire the execution completion event 
181-             ( dnd  !==  true )  &&  bridge . dispatch ( executionEventName ,  err  ||  null ,  execution ) ; 
195+ 
196+             // Note: We are sending null to dispatchEvent function 
197+             // because this event should be fired even if shouldSkipExecution is true as this event is 
198+             // used to complete the execution in the sandbox. All other events are fired only if 
199+             // shouldSkipExecution is false. 
200+             ( dnd  !==  true )  &&  bridge . dispatch ( null , 
201+                 executionEventName ,  err  ||  null ,  execution ) ; 
182202        } ) ; 
183203
184204        // if a timeout is set, we must ensure that all pending timers are cleared and an execution timeout event is 
@@ -207,14 +227,19 @@ module.exports = function (bridge, glob) {
207227        executeContext ( scope ,  code ,  execution , 
208228            // if a console is sent, we use it. otherwise this also prevents erroneous referencing to any console 
209229            // inside this closure. 
210-             ( new  PostmanConsole ( bridge ,  options . cursor ,  options . debug  &&  glob . console ) ) , 
230+             ( new  PostmanConsole ( bridge ,  options . cursor ,  options . debug  &&  glob . console ,   execution ) ) , 
211231            timers , 
212232            ( 
213233                new  PostmanAPI ( execution ,  function  ( request ,  callback )  { 
214234                    var  eventId  =  timers . setEvent ( callback ) ; 
215235
216-                     bridge . dispatch ( executionRequestEventName ,  options . cursor ,  id ,  eventId ,  request ) ; 
217-                 } ,  dispatchAssertions ,  new  PostmanCookieStore ( id ,  bridge ,  timers ) ,  { 
236+                     bridge . dispatch ( execution ,  executionRequestEventName ,  options . cursor ,  id ,  eventId ,  request ) ; 
237+                 } , 
238+                 /* onSkipRequest = */  ( )  =>  { 
239+                     execution . shouldSkipExecution  =  true ; 
240+                     timers . terminate ( null ) ; 
241+                 } , 
242+                 dispatchAssertions ,  new  PostmanCookieStore ( id ,  bridge ,  timers ,  execution ) ,  { 
218243                    disabledAPIs : initializationOptions . disabledAPIs 
219244                } ) 
220245            ) , 
0 commit comments