DSDSWeb/static/js/Cesium-1.53/Specs/Core/IonResourceSpec.js

326 lines
13 KiB
JavaScript

defineSuite([
'Core/IonResource',
'Core/Ion',
'Core/RequestErrorEvent',
'Core/Resource',
'Core/RuntimeError',
'ThirdParty/when'
], function(
IonResource,
Ion,
RequestErrorEvent,
Resource,
RuntimeError,
when) {
'use strict';
var assetId = 123890213;
var endpoint = {
type: '3DTILES',
url: 'https://assets.cesium.com/' + assetId + '/tileset.json',
accessToken: 'not_really_a_refresh_token',
attributions: []
};
it('constructs with expected values', function() {
spyOn(Resource, 'call').and.callThrough();
var endpointResource = IonResource._createEndpointResource(assetId);
var resource = new IonResource(endpoint, endpointResource);
expect(resource).toBeInstanceOf(Resource);
expect(resource._ionEndpoint).toEqual(endpoint);
expect(Resource.call).toHaveBeenCalledWith(resource, {
url: endpoint.url,
retryCallback: resource.retryCallback,
retryAttempts: 1
});
});
it('clone works', function() {
var endpointResource = IonResource._createEndpointResource(assetId);
var resource = new IonResource(endpoint, endpointResource);
var cloned = resource.clone();
expect(cloned).not.toBe(resource);
expect(cloned._ionRoot).toBe(resource);
cloned._ionRoot = undefined;
expect(cloned.retryCallback).toBe(resource.retryCallback);
expect(cloned.headers.Authorization).toBe(resource.headers.Authorization);
expect(cloned).toEqual(resource);
});
it('create creates the expected resource', function() {
var endpointResource = IonResource._createEndpointResource(assetId);
var resource = new IonResource(endpoint, endpointResource);
expect(resource.getUrlComponent()).toEqual(endpoint.url);
expect(resource._ionEndpoint).toBe(endpoint);
expect(resource._ionEndpointResource).toEqual(endpointResource);
expect(resource.retryCallback).toBeDefined();
expect(resource.retryAttempts).toBe(1);
});
it('fromAssetId calls constructor for non-external endpoint with expected parameters', function() {
var tilesAssetId = 123890213;
var tilesEndpoint = {
type: '3DTILES',
url: 'https://assets.cesium.com/' + tilesAssetId + '/tileset.json',
accessToken: 'not_really_a_refresh_token',
attributions: []
};
var options = {};
var resourceEndpoint = IonResource._createEndpointResource(tilesAssetId, options);
spyOn(IonResource, '_createEndpointResource').and.returnValue(resourceEndpoint);
spyOn(resourceEndpoint, 'fetchJson').and.returnValue(when.resolve(tilesEndpoint));
return IonResource.fromAssetId(tilesAssetId, options)
.then(function(resource) {
expect(IonResource._createEndpointResource).toHaveBeenCalledWith(tilesAssetId, options);
expect(resourceEndpoint.fetchJson).toHaveBeenCalled();
expect(resource._ionEndpointResource).toEqual(resourceEndpoint);
expect(resource._ionEndpoint).toEqual(tilesEndpoint);
});
});
function testNonImageryExternalResource(externalEndpoint) {
var resourceEndpoint = IonResource._createEndpointResource(123890213);
spyOn(IonResource, '_createEndpointResource').and.returnValue(resourceEndpoint);
spyOn(resourceEndpoint, 'fetchJson').and.returnValue(when.resolve(externalEndpoint));
return IonResource.fromAssetId(123890213)
.then(function(resource) {
expect(resource.url).toEqual(externalEndpoint.options.url);
expect(resource.headers.Authorization).toBeUndefined();
expect(resource.retryCallback).toBeUndefined();
});
}
it('fromAssetId returns basic Resource for external 3D tilesets', function() {
return testNonImageryExternalResource({
type: '3DTILES',
externalType: '3DTILES',
options: { url: 'http://test.invalid/tileset.json' },
attributions: []
});
});
it('fromAssetId returns basic Resource for external 3D tilesets', function() {
return testNonImageryExternalResource({
type: 'TERRAIN',
externalType: 'STK_TERRAIN_SERVER',
options: { url: 'http://test.invalid/world' },
attributions: []
});
});
it('fromAssetId rejects for external imagery', function() {
return testNonImageryExternalResource({
type: 'IMAGERY',
externalType: 'URL_TEMPLATE',
url: 'http://test.invalid/world',
attributions: []
})
.then(fail)
.otherwise(function(e) {
expect(e).toBeInstanceOf(RuntimeError);
});
});
it('createEndpointResource creates expected values with default parameters', function() {
var assetId = 2348234;
var resource = IonResource._createEndpointResource(assetId);
expect(resource.url).toBe(Ion.defaultServer.url + 'v1/assets/' + assetId + '/endpoint?access_token=' + Ion.defaultAccessToken);
});
it('createEndpointResource creates expected values with overridden options', function() {
var serverUrl = 'https://api.cesium.test/';
var accessToken = 'not_a_token';
var assetId = 2348234;
var resource = IonResource._createEndpointResource(assetId, { server: serverUrl, accessToken: accessToken });
expect(resource.url).toBe(serverUrl + 'v1/assets/' + assetId + '/endpoint?access_token=' + accessToken);
});
it('createEndpointResource creates expected values with overridden defaults', function() {
var defaultServer = Ion.defaultServer;
var defaultAccessToken = Ion.defaultAccessToken;
Ion.defaultServer = new Resource({ url: 'https://api.cesium.test/' });
Ion.defaultAccessToken = 'not_a_token';
var assetId = 2348234;
var resource = IonResource._createEndpointResource(assetId);
expect(resource.url).toBe(Ion.defaultServer.url + 'v1/assets/' + assetId + '/endpoint?access_token=' + Ion.defaultAccessToken);
Ion.defaultServer = defaultServer;
Ion.defaultAccessToken = defaultAccessToken;
});
it('Calls base _makeRequest with expected options when resource no Accept header is already defined', function() {
var originalOptions = {};
var expectedOptions = {
headers: {
Accept: '*/*;access_token=' + endpoint.accessToken
}
};
var _makeRequest = spyOn(Resource.prototype, '_makeRequest');
var endpointResource = IonResource._createEndpointResource(assetId);
var resource = new IonResource(endpoint, endpointResource);
resource._makeRequest(originalOptions);
expect(_makeRequest).toHaveBeenCalledWith(expectedOptions);
});
it('Calls base _makeRequest with expected options when resource Accept header is already defined', function() {
var originalOptions = {};
var expectedOptions = {
headers: {
Accept: 'application/json,*/*;access_token=' + endpoint.accessToken
}
};
var _makeRequest = spyOn(Resource.prototype, '_makeRequest');
var endpointResource = IonResource._createEndpointResource(assetId);
var resource = new IonResource(endpoint, endpointResource);
resource.headers.Accept = 'application/json';
resource._makeRequest(originalOptions);
expect(_makeRequest).toHaveBeenCalledWith(expectedOptions);
});
it('Calls base _makeRequest with expected options when options header.Accept is already defined', function() {
var originalOptions = {
headers: {
Accept: 'application/json'
}
};
var expectedOptions = {
headers: {
Accept: 'application/json,*/*;access_token=' + endpoint.accessToken
}
};
var _makeRequest = spyOn(Resource.prototype, '_makeRequest');
var endpointResource = IonResource._createEndpointResource(assetId);
var resource = new IonResource(endpoint, endpointResource);
resource._makeRequest(originalOptions);
expect(_makeRequest).toHaveBeenCalledWith(expectedOptions);
});
it('Calls base _makeRequest with no changes for external assets', function() {
var externalEndpoint = {
type: '3DTILES',
externalType: '3DTILES',
options: { url: 'http://test.invalid/tileset.json' },
attributions: []
};
var options = {};
var _makeRequest = spyOn(Resource.prototype, '_makeRequest');
var endpointResource = IonResource._createEndpointResource(assetId);
var resource = new IonResource(externalEndpoint, endpointResource);
resource._makeRequest(options);
expect(_makeRequest.calls.argsFor(0)[0]).toBe(options);
});
it('Calls base fetchImage with preferBlob for ion assets', function() {
var fetchImage = spyOn(Resource.prototype, 'fetchImage');
var endpointResource = IonResource._createEndpointResource(assetId);
var resource = new IonResource(endpoint, endpointResource);
resource.fetchImage(false, true);
expect(fetchImage).toHaveBeenCalledWith(true, true);
});
it('Calls base fetchImage with no changes for external assets', function() {
var externalEndpoint = {
type: '3DTILES',
externalType: '3DTILES',
options: { url: 'http://test.invalid/tileset.json' },
attributions: []
};
var fetchImage = spyOn(Resource.prototype, 'fetchImage');
var endpointResource = IonResource._createEndpointResource(assetId);
var resource = new IonResource(externalEndpoint, endpointResource);
resource.fetchImage(false, true);
expect(fetchImage).toHaveBeenCalledWith(false, true);
});
describe('retryCallback', function() {
var endpointResource;
var resource;
var retryCallback;
beforeEach(function() {
endpointResource = new Resource({ url: 'https://api.test.invalid', access_token: 'not_the_token' });
resource = new IonResource(endpoint, endpointResource);
retryCallback = resource.retryCallback;
});
it('returns false when error is undefined', function() {
return retryCallback(resource, undefined).then(function(result) {
expect(result).toBe(false);
});
});
it('returns false when error is non-401', function() {
var error = new RequestErrorEvent(404);
return retryCallback(resource, error).then(function(result) {
expect(result).toBe(false);
});
});
it('returns false when error is event with non-Image target', function() {
var event = { target: {} };
return retryCallback(resource, event).then(function(result) {
expect(result).toBe(false);
});
});
function testCallback(resource, event) {
var deferred = when.defer();
spyOn(endpointResource, 'fetchJson').and.returnValue(deferred.promise);
var newEndpoint = {
type: '3DTILES',
url: 'https://assets.cesium.com/' + assetId,
accessToken: 'not_not_really_a_refresh_token'
};
var promise = retryCallback(resource, event);
var resultPromise = promise.then(function(result) {
expect(result).toBe(true);
expect(resource._ionEndpoint).toBe(newEndpoint);
});
expect(endpointResource.fetchJson).toHaveBeenCalledWith();
//A second retry should re-use the same pending promise
var promise2 = retryCallback(resource, event);
expect(promise._pendingPromise).toBe(promise2._pendingPromise);
deferred.resolve(newEndpoint);
return resultPromise;
}
it('works when error is a 401', function() {
var error = new RequestErrorEvent(401);
return testCallback(resource, error);
});
it('works when error is event with Image target', function() {
var event = { target: new Image() };
return testCallback(resource, event);
});
it('works with derived resource and sets root access_token', function() {
var derived = resource.getDerivedResource('1');
var error = new RequestErrorEvent(401);
return testCallback(derived, error)
.then(function(){
expect(derived._ionEndpoint).toBe(resource._ionEndpoint);
expect(derived.headers.Authorization).toEqual(resource.headers.Authorization);
});
});
});
});