'use strict'; function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } } /** * Licensed Materials - Property of IBM * IBM Business Analytics (C) Copyright IBM Corp. 2020 * US Government Users Restricted Rights - Use, duplication or disclosure restricted by GSA ADP Schedule Contract with IBM Corp. */ /** * @class DashboardContentService * @hideconstructor * * @classdesc * CA dashboard content service oprations: getAncestors, onSaveAsSuccess, Save, SaveAs, SaveThumbnail */ define(['../../dashboard/glass/util/SaveActionUtil', '../../app/util/GlassUtil', '../../app/nls/StringResources', '../../dashboard/loader/DeploymentReferencesUtil'], function (SaveActionUtil, GlassUtil, StringResources, DeploymentReferencesUtil) { return function () { function DashboardContentService() { _classCallCheck(this, DashboardContentService); } DashboardContentService.prototype.initialize = function initialize(glassContext) { this._glassContext = glassContext; return Promise.resolve(); }; /** * Given a dashboard board Id or Url, return the dashboard's parent path information (Ancestors) * @async * @param {Object} spec - JSON object that is used to locate a dashboard object * spec.id - board id * spec.url - url of the dashboard * spec.url is used only when avaiable, otherwise spec.id is used. * @return {Promise} - resolved with an array of parent path ancestors. * The array is null when there is no id specified or when an error occurred while retrieving them */ DashboardContentService.prototype.getAncestors = function getAncestors() { var _this = this; var spec = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {}; var id = spec.id, url = spec.url; if (!id && !url) { return Promise.resolve(null); } else { return this._getContentService().then(function (oContentService) { var server_URL = url || oContentService.getBaseObjectsURL() + '/' + id; var options = { data: { fields: 'ancestors' } }; return oContentService.get(server_URL, options); }).then(function (result) { return Promise.resolve(result ? result.data[0].ancestors || null : null); }).catch(function (error) { _this._logError('Error retrieving ancestors:', error); return null; }); } }; /** * Given the id or url of a dashboard, return the dashboard information * @param {String} boardId - dashboard Id * @param {String} boardUrl - dashboard Url (search path) * @returns {Promise} - Resolved dashboard information { id, name, searchPath, permissions, boardSpec } */ DashboardContentService.prototype.getDashboard = function getDashboard(boardId, boardUrl) { var _this2 = this; var url = boardUrl || 'v1/objects/' + boardId; var options = { dataType: 'json', data: { 'fields': ['defaultName', 'specification', 'searchPath', 'deploymentReferences.ancestors', 'deploymentReferences.defaultName', 'deploymentReferences.id', 'deploymentReferences.type', 'deploymentReferences.searchPath'].join(',') }, MRUInfo: {} }; return this._getBoardSpecFromContentSvc(url, options).then(function (response) { return _this2._handleBoardSpecResponse(response); }); }; /** * Callback of Save As success * Given a dashboard board id or a dashboard url, return the dashboard spec * @async * @param {Object} spec - JSON object that is used to locate a dashboard object * spec.id - board id * spec.url - url of the dashboard * spec.url is used only when avaiable, otherwise spec.id is used. * @return {Promise} - resolved with dashboard information of permissions and boardId * @example * permissions is an array that contains elements such as "execute", "read", "setPolicy", "traverse", "write" */ DashboardContentService.prototype.onSaveAsSuccess = function onSaveAsSuccess() { var spec = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {}; var id = spec.id, url = spec.url; if (!id && !url) { return Promise.resolve(null); } else { return this._getContentService().then(function (oContentService) { var server_URL = url || oContentService.getBaseObjectsURL() + '/' + id; var oGetOptions = { dataType: 'json', data: { 'fields': 'defaultName,specification' }, MRUInfo: {} }; return oContentService.get(server_URL, oGetOptions); }).then(function (response) { var data = response && response.data && response.data.length > 0 ? response.data[0] : {}; return Promise.resolve({ permissions: data.permissions, id: data.id }); }); } }; /** * Update an existing Dashboard object * @async * @param {DashboardAPI} dashboard api * @return {Promise} Resolved object is the saved spec * @example when failed, the promise will reject an XHR request object { readyState: 4 getResponseHeader: ƒ (e) getAllResponseHeaders: ƒ () setRequestHeader: ƒ (e,t) overrideMimeType: ƒ (e) statusCode: ƒ (e) .. } * */ DashboardContentService.prototype.saveDashboard = function saveDashboard(dashboard, assetId) { var _this3 = this; var spec = dashboard.getFeature('Serializer').toJSON(); var cmSpec = this._getCMSpec(spec, dashboard); return new Promise(function (resolve, reject) { _this3._getContentService().then(function (oContentService) { return oContentService.put('v1/objects/' + assetId + '?ignoreInvalidObjectReference=true', { contentType: 'application/json', processData: false, dataType: 'application/json', data: JSON.stringify(cmSpec), MRUInfo: {} //A necessary property to support MRU }).fail(function (deferred, request) { reject(request); }).then(function () { resolve({ 'savedSpec': cmSpec.specification, 'status': 'success' }); }); }); }); }; /** * CREATE a new Dashboard object * @async * @param {DashboardAPI} dashboard api * @param {string} name of the dashboard * @param {string} url of the dashboard's parent * @param {boolean} True means save as an existing dashboard * @return {Promise} * @exmaple when failed, the promise rejects an error object like below * { 'status': 'fail', 'saveRequest': request, 'cmSpec': cmSpec } */ DashboardContentService.prototype.saveAsDashboard = function saveAsDashboard(dashboard, name, url, overwrite) { var ajaxService = GlassUtil.getAjaxService(this._glassContext); //enable the 'more' button containing the set as home if it is not already enabled var moreButton = this._glassContext.appController.findPlugin('com.ibm.bi.glass.common.operations'); if (moreButton && !moreButton.isEnabled) { moreButton.enable(); } return SaveActionUtil.saveAs({ ajaxService: ajaxService, name: name, url: url, dashboard: dashboard, overwrite: overwrite }); }; /** * Save the thumbnail image into a Databoard Object * @async * @param {Object} spec * spec.thumbnailDataUri - base64 encoded PNG * spec.id - board Id of a dashboard * @return {Promise} */ DashboardContentService.prototype.saveThumbnail = function saveThumbnail() { var _this4 = this; var spec = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {}; var thumbnailDataUri = spec.thumbnailDataUri, id = spec.id; var dataUriParts = thumbnailDataUri && thumbnailDataUri.split(','); if (!dataUriParts || dataUriParts.length != 2) { this._logError('Invalid thumbnail returned from Thumbnail service.'); return; } if (!id) { this._logError('Dashboard id is undefined when generating thumbnail.'); return; } return this._getContentService().then(function (oContentService) { return _this4._getAjaxService().post(oContentService.getBaseObjectsURL() + '/' + id + '/items?updateAction=update', { contentType: 'application/json', processData: false, dataType: 'text', data: JSON.stringify({ defaultName: 'thumbnail', type: 'graphic', dataType: 'image/png', data: dataUriParts[1] }) }); }); }; /** * Process board spec response from content service. * @private * @param {Object} response - The response of a successful board spec request to content service * @return {Promise} - Resolved with a JSON object that contains the dashboard informaiton * @example { boardSpec: {xxx}, boardId: 'i12345678', permissions: ['execute','read','setPolicy','traverse', 'write'], searchPath: 'CAMID("LDAP:u:uid=hmiller,ou=people")/folder[@name=\'My Folders\']/exploration[@name=\'New dashboard1\']', name: 'New dashboard1' } */ DashboardContentService.prototype._handleBoardSpecResponse = function _handleBoardSpecResponse(response) { //No response data if (response.data.length === 0) { return Promise.reject({ code: 'notFound', message: StringResources.get('noDashboardFound') }); } //No read and execute permissions var permissions = response.data[0].permissions; if (!this._hasPermission(permissions)) { return Promise.reject({ code: 'noPermission', message: StringResources.get('noDashboardPermission') }); } // should never have a dashboard with null spec... but just in case var responseData = response.data[0]; var specAsString = responseData.specification || '{}'; var boardSpec = JSON.parse(specAsString); boardSpec._meta = { bundleID: responseData.id }; //Update deployment reference DeploymentReferencesUtil.updateIds(boardSpec, responseData.deploymentReferences); boardSpec.features = boardSpec.features || {}; boardSpec.features.ContentStoreReferences = responseData.deploymentReferences; return Promise.resolve({ boardSpec: boardSpec, boardId: responseData.id, permissions: responseData.permissions, searchPath: responseData.searchPath, name: responseData.defaultName }); }; DashboardContentService.prototype._hasPermission = function _hasPermission(permissions) { if (Array.isArray(permissions) && permissions.length) { return ['read', 'execute'].every(function (permission) { return permissions.indexOf(permission) !== -1; }); } return false; }; /** * Fetches the board spec using the content service. * Wrapping the Content Service JQuery deferred in a native Promise to obtain some predictable error handling * @param {String} url - URL of dashboard resource to fetch * @param {String} options - Options to pass into the get request * @return {Promise} - A Promise which is resolved once the board spec is fetched * when failed, it rejects with the error status, error code and error messages. */ DashboardContentService.prototype._getBoardSpecFromContentSvc = function _getBoardSpecFromContentSvc(url, options) { var _this5 = this; return new Promise(function (resolve, reject) { _this5._getContentService().then(function (contentSvc) { contentSvc.get(url, options).done(resolve).fail(function (ajaxdfd, jqXHR, textStatus) { reject({ status: jqXHR.status, code: textStatus, message: StringResources.get('noDashboardFound') }); }); }); }); }; /** *This function is overriden in StoryContentSerivce *@private *@param {Object} spec - board spec of a dashboard *@return the dashboard CM spec */ DashboardContentService.prototype._getCMSpec = function _getCMSpec(spec, dashboard) { var boardModel = dashboard.getFeature('internal').getBoardModel(); return SaveActionUtil.getCMSpec(spec, boardModel, false); }; DashboardContentService.prototype._logError = function _logError(errMsg) { this._glassContext.getCoreSvc('.Logger').error(errMsg); }; DashboardContentService.prototype._getContentService = function _getContentService() { return this._glassContext.getSvc('.Content'); }; DashboardContentService.prototype._getAjaxService = function _getAjaxService() { return this._glassContext.services.ajax; }; DashboardContentService.prototype._getDashboardApi = function _getDashboardApi() { return this._getCurrentView().getDashboardApi(); }; DashboardContentService.prototype._getCurrentView = function _getCurrentView() { return this._glassContext.appController.currentAppView.currentContentView; }; return DashboardContentService; }(); }); //# sourceMappingURL=DashboardContentService.js.map