angular/packages/zone.js/test/common/fetch.spec.ts
Kristiyan Kostadinov 41223a81f2 build: update to jasmine 4.0 (#45558)
Updates us to version 4.0 of Jasmine and fixes some errors that were the result of us depending upon deprecated APIs. We need to do this both to stay up to date and because it was going to break eventually, because one of the Bazel packages was logging a deprecation warning that version 4.0 was required.

There were also some cases where the state of `ngDevMode` had started leaking out between tests.

PR Close #45558
2022-04-11 16:25:28 +00:00

219 lines
8.7 KiB
TypeScript

/**
* @license
* Copyright Google LLC All Rights Reserved.
*
* Use of this source code is governed by an MIT-style license that can be
* found in the LICENSE file at https://angular.io/license
*/
import {ifEnvSupports, ifEnvSupportsWithDone, isFirefox, isSafari} from '../test-util';
declare const global: any;
describe(
'fetch', ifEnvSupports('fetch', function() {
let testZone: Zone;
beforeEach(() => {
testZone = Zone.current.fork({name: 'TestZone'});
});
it('should work for text response', function(done) {
testZone.run(function() {
global['fetch']('/base/angular/packages/zone.js/test/assets/sample.json')
.then(function(response: any) {
const fetchZone = Zone.current;
expect(fetchZone.name).toBe(testZone.name);
response.text().then(function(text: string) {
expect(Zone.current.name).toBe(fetchZone.name);
expect(text.trim()).toEqual('{"hello": "world"}');
done();
});
});
});
});
it('should work for json response', function(done) {
testZone.run(function() {
global['fetch']('/base/angular/packages/zone.js/test/assets/sample.json')
.then(function(response: any) {
const fetchZone = Zone.current;
expect(fetchZone.name).toBe(testZone.name);
response.json().then(function(obj: any) {
expect(Zone.current.name).toBe(fetchZone.name);
expect(obj.hello).toEqual('world');
done();
});
});
});
});
it('should work for blob response', function(done) {
testZone.run(function() {
global['fetch']('/base/angular/packages/zone.js/test/assets/sample.json')
.then(function(response: any) {
const fetchZone = Zone.current;
expect(fetchZone.name).toBe(testZone.name);
// Android 4.3- doesn't support response.blob()
if (response.blob) {
response.blob().then(function(blob: any) {
expect(Zone.current.name).toBe(fetchZone.name);
expect(blob instanceof Blob).toEqual(true);
done();
});
} else {
done();
}
});
});
});
it('should work for arrayBuffer response', function(done) {
testZone.run(function() {
global['fetch']('/base/angular/packages/zone.js/test/assets/sample.json')
.then(function(response: any) {
const fetchZone = Zone.current;
expect(fetchZone.name).toBe(testZone.name);
// Android 4.3- doesn't support response.arrayBuffer()
if (response.arrayBuffer) {
response.arrayBuffer().then(function(blob: any) {
expect(Zone.current).toBe(fetchZone);
expect(blob instanceof ArrayBuffer).toEqual(true);
done();
});
} else {
done();
}
});
});
});
it('should throw error when send crendential',
ifEnvSupportsWithDone(isFirefox, function(done: DoneFn) {
testZone.run(function() {
global['fetch']('http://user:password@example.com')
.then(
function(response: any) {
fail('should not success');
},
(error: any) => {
expect(Zone.current.name).toEqual(testZone.name);
expect(error.constructor.name).toEqual('TypeError');
done();
});
});
}));
describe('macroTask', () => {
const logs: string[] = [];
let fetchZone: Zone;
let fetchTask: any = null;
beforeEach(() => {
logs.splice(0);
fetchZone = Zone.current.fork({
name: 'fetch',
onScheduleTask: (delegate: ZoneDelegate, curr: Zone, target: Zone, task: Task) => {
if (task.type !== 'eventTask') {
logs.push(`scheduleTask:${task.source}:${task.type}`);
}
if (task.source === 'fetch') {
fetchTask = task;
}
return delegate.scheduleTask(target, task);
},
onInvokeTask:
(delegate: ZoneDelegate, curr: Zone, target: Zone, task: Task, applyThis: any,
applyArgs: any) => {
if (task.type !== 'eventTask') {
logs.push(`invokeTask:${task.source}:${task.type}`);
}
return delegate.invokeTask(target, task, applyThis, applyArgs);
},
onCancelTask: (delegate: ZoneDelegate, curr: Zone, target: Zone, task: Task) => {
if (task.type !== 'eventTask') {
logs.push(`cancelTask:${task.source}:${task.type}`);
}
return delegate.cancelTask(target, task);
}
});
});
it('fetch should be considered as macroTask', (done: DoneFn) => {
fetchZone.run(() => {
global['fetch']('/base/angular/packages/zone.js/test/assets/sample.json')
.then(function(response: any) {
expect(Zone.current.name).toBe(fetchZone.name);
expect(logs).toEqual([
'scheduleTask:fetch:macroTask', 'scheduleTask:Promise.then:microTask',
'invokeTask:Promise.then:microTask', 'invokeTask:fetch:macroTask',
'scheduleTask:Promise.then:microTask', 'invokeTask:Promise.then:microTask'
]);
done();
});
});
});
it('cancel fetch should invoke onCancelTask',
ifEnvSupportsWithDone('AbortController', (done: DoneFn) => {
if (isSafari()) {
// safari not work with AbortController
done();
return;
}
fetchZone.run(() => {
const AbortController = global['AbortController'];
const abort = new AbortController();
const signal = abort.signal;
global['fetch']('/base/angular/packages/zone.js/test/assets/sample.json', {signal})
.then(function(response: any) {
fail('should not get response');
})
.catch(function(error: any) {
expect(error.name).toEqual('AbortError');
expect(logs).toEqual([
'scheduleTask:fetch:macroTask', 'cancelTask:fetch:macroTask',
'scheduleTask:Promise.then:microTask', 'invokeTask:Promise.then:microTask',
'scheduleTask:Promise.then:microTask', 'invokeTask:Promise.then:microTask',
'scheduleTask:Promise.then:microTask', 'invokeTask:Promise.then:microTask'
]);
done();
});
abort.abort();
});
}));
it('cancel fetchTask should trigger abort',
ifEnvSupportsWithDone('AbortController', (done: DoneFn) => {
if (isSafari()) {
// safari not work with AbortController
done();
return;
}
fetchZone.run(() => {
const AbortController = global['AbortController'];
const abort = new AbortController();
const signal = abort.signal;
global['fetch']('/base/angular/packages/zone.js/test/assets/sample.json', {signal})
.then(function(response: any) {
fail('should not get response');
})
.catch(function(error: any) {
expect(error.name).toEqual('AbortError');
expect(logs).toEqual([
'scheduleTask:fetch:macroTask', 'cancelTask:fetch:macroTask',
'scheduleTask:Promise.then:microTask', 'invokeTask:Promise.then:microTask',
'scheduleTask:Promise.then:microTask', 'invokeTask:Promise.then:microTask',
'scheduleTask:Promise.then:microTask', 'invokeTask:Promise.then:microTask'
]);
done();
});
fetchTask.zone.cancelTask(fetchTask);
});
}));
});
}, emptyRun));
function emptyRun() {
// Jasmine will throw if there are no tests.
it('should pass', () => {});
}