@@ -96,6 +96,7 @@ Zone.__load_patch('XHR', (global: any, Zone: ZoneType) => {
9696 const XHR_LISTENER = zoneSymbol ( 'xhrListener' ) ;
9797 const XHR_SCHEDULED = zoneSymbol ( 'xhrScheduled' ) ;
9898 const XHR_URL = zoneSymbol ( 'xhrURL' ) ;
99+ const XHR_ERROR_BEFORE_SCHEDULED = zoneSymbol ( 'xhrErrorBeforeScheduled' ) ;
99100
100101 interface XHROptions extends TaskData {
101102 target : any ;
@@ -126,9 +127,10 @@ Zone.__load_patch('XHR', (global: any, Zone: ZoneType) => {
126127 const SCHEDULED = 'scheduled' ;
127128
128129 function scheduleTask ( task : Task ) {
129- ( XMLHttpRequest as any ) [ XHR_SCHEDULED ] = false ;
130130 const data = < XHROptions > task . data ;
131131 const target = data . target ;
132+ target [ XHR_SCHEDULED ] = false ;
133+ target [ XHR_ERROR_BEFORE_SCHEDULED ] = false ;
132134 // remove existing event listener
133135 const listener = target [ XHR_LISTENER ] ;
134136 if ( ! oriAddListener ) {
@@ -143,7 +145,7 @@ Zone.__load_patch('XHR', (global: any, Zone: ZoneType) => {
143145 if ( target . readyState === target . DONE ) {
144146 // sometimes on some browsers XMLHttpRequest will fire onreadystatechange with
145147 // readyState=4 multiple times, so we need to check task state here
146- if ( ! data . aborted && ( XMLHttpRequest as any ) [ XHR_SCHEDULED ] && task . state === SCHEDULED ) {
148+ if ( ! data . aborted && target [ XHR_SCHEDULED ] && task . state === SCHEDULED ) {
147149 // check whether the xhr has registered onload listener
148150 // if that is the case, the task should invoke after all
149151 // onload listeners finish.
@@ -167,6 +169,9 @@ Zone.__load_patch('XHR', (global: any, Zone: ZoneType) => {
167169 } else {
168170 task . invoke ( ) ;
169171 }
172+ } else if ( ! data . aborted && target [ XHR_SCHEDULED ] === false ) {
173+ // error occurs when xhr.send()
174+ target [ XHR_ERROR_BEFORE_SCHEDULED ] = true ;
170175 }
171176 }
172177 } ;
@@ -177,7 +182,7 @@ Zone.__load_patch('XHR', (global: any, Zone: ZoneType) => {
177182 target [ XHR_TASK ] = task ;
178183 }
179184 sendNative ! . apply ( target , data . args ) ;
180- ( XMLHttpRequest as any ) [ XHR_SCHEDULED ] = true ;
185+ target [ XHR_SCHEDULED ] = true ;
181186 return task ;
182187 }
183188
@@ -215,8 +220,15 @@ Zone.__load_patch('XHR', (global: any, Zone: ZoneType) => {
215220 } else {
216221 const options : XHROptions =
217222 { target : self , url : self [ XHR_URL ] , isPeriodic : false , args : args , aborted : false } ;
218- return scheduleMacroTaskWithCurrentZone (
223+ const task = scheduleMacroTaskWithCurrentZone (
219224 XMLHTTPREQUEST_SOURCE , placeholderCallback , options , scheduleTask , clearTask ) ;
225+ if ( self && self [ XHR_ERROR_BEFORE_SCHEDULED ] === true && ! options . aborted &&
226+ task . state === SCHEDULED ) {
227+ // xhr request throw error when send
228+ // we should invoke task instead of leaving a scheduled
229+ // pending macroTask
230+ task . invoke ( ) ;
231+ }
220232 }
221233 } ) ;
222234
0 commit comments