123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337 |
- '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 Cognos Products: Dashboard
- * | (C) Copyright IBM Corp. 2018, 2020
- * |
- * | US Government Users Restricted Rights - Use, duplication or disclosure
- * | restricted by GSA ADP Schedule Contract with IBM Corp.
- * +------------------------------------------------------------------------+
- */
- define(['underscore', 'bi/moser/moser.min', '../../apiHelpers/SlotAPIHelper'], function (_, MoserJS, SlotAPIHelper) {
- var _class, _temp;
- var SOURCE_TYPES_TO_VERIFY_JOIN = [MoserJS.default.UseSpecType.FILE.value(), MoserJS.default.UseSpecType.DATASET.value()];
- var DatasourceUtil = (_temp = _class = function () {
- function DatasourceUtil() {
- _classCallCheck(this, DatasourceUtil);
- }
- /**
- * We agreed only do client level join for uploaded files and data sets (dataset2),
- * or a module created from uploaded files or data sets (dataset2).
- * @returns true if items are from source types in SOURCE_TYPES_TO_VERIFY_JOIN
- */
- DatasourceUtil._shouldVerifyJoin = function _shouldVerifyJoin(module) {
- var items = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : [];
- var moserDataSources = arguments[2];
- var newAPI = !!(module.getInterfaceType && module.getImplType);
- if (newAPI) {
- var dataSourceId = module.getId();
- var verifyJoin = true;
- for (var i = 0; i < items.length && verifyJoin; i++) {
- var columnId = items[i];
- var metadataColumn = module.getMetadataColumn(columnId);
- var table = metadataColumn ? metadataColumn.getTableName() : null;
- if (!metadataColumn || !table) {
- // Skip if not a metadata column or metadata column is not from a table, e.g. stand alone model calculations.
- verifyJoin = false;
- break;
- }
- var originalType = moserDataSources.getOriginalSourceType(dataSourceId, columnId);
- if (originalType && SOURCE_TYPES_TO_VERIFY_JOIN.indexOf(originalType) === -1) {
- verifyJoin = false;
- break;
- }
- }
- return verifyJoin;
- } else {
- var theMoserJS = DatasourceUtil.MoserJS_Inst || MoserJS;
- var tables = [];
- return _.find(items, function (columnId) {
- if (!DatasourceUtil.isMultiMeasuresSeriesOrValue(columnId)) {
- var _metadataColumn = module.getMetadataColumn(columnId);
- var _table = _metadataColumn ? _metadataColumn.getTable() : null;
- if (!_metadataColumn || !_table) {
- return true;
- }
- // Do not check again if already checked
- if (tables.indexOf(_table.idForExpression) === -1) {
- tables.push(_table.idForExpression);
- var useSpec = theMoserJS.default.ModuleUtils.getObjectUseSpec(_table);
- if (useSpec) {
- // Return if there is a source type not belongs to the local join
- return SOURCE_TYPES_TO_VERIFY_JOIN.indexOf(useSpec.getType().value()) === -1;
- }
- }
- }
- }) === undefined;
- }
- };
- DatasourceUtil.isMultiMeasuresSeriesOrValue = function isMultiMeasuresSeriesOrValue(itemId) {
- return itemId.indexOf(SlotAPIHelper.MULTI_MEASURES_SERIES) === 0 || itemId.indexOf(SlotAPIHelper.MULTI_MEASURES_VALUE) === 0;
- };
- DatasourceUtil.getTableRef = function getTableRef(dataSource, itemIds) {
- var names = [];
- if (dataSource) {
- itemIds.forEach(function (item) {
- var metadataColumn = dataSource.getMetadataColumn(item);
- var tableName = metadataColumn && metadataColumn.getTableName();
- if (tableName && names.indexOf(tableName) === -1) {
- names.push(tableName);
- }
- });
- }
- return names;
- };
- /**
- *
- * @param {object} module - the data source module, either an uploaded file, a dataset, a package, a module, or a model built from an uploaded file, a dataset, a package, or a module
- * @param {object[]} projectedItems - An array of projected items ids
- * @param return true if metadata columns referenced by pageContextItemSpec and dataSlots are from:
- * 1) uploaded files
- * 2) data sets
- * 3) the combination of 1) and 2).
- */
- DatasourceUtil.isSupportedNonJoinTableDatascourceType = function isSupportedNonJoinTableDatascourceType(module) {
- var itemIds = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : [];
- if (!module || module.getSourceType() === 'package' || itemIds.length === 0) {
- return false;
- }
- return DatasourceUtil._shouldVerifyJoin(module, itemIds);
- };
- /**
- * A dashboard works against one MUI module created on the fly each time a dashboard is created.
- * A package is a metadata model that have not the necessary table joins applied at the database level.
- * Therefore dashboards need not worry about these joins.
- * A dashboard only handle join relationships at the data module level.
- * MUI creates a module which can be one of:
- * 1) contain one single package, this is the simplest case
- * 2) uploaded file containing more than one table where there are no joins between tables. In Endor, all tables within an uploaded xlsx are not joined
- * 3) a data module containing any combination of packgages, other modules, uploaded files and data sets. This is the complex case.
- *
- * For Endor release, decision is made to only verify table joins for uploaded files and data sets since currently there is no API to get accurate
- * join relationships for case3).
- *
- * @param return true if metadata columns referenced by pageContextItemSpec and dataSlots are from:
- * 1) uploaded files
- * 2) data sets
- * 3) the combination of 1) and 2).
- */
- DatasourceUtil.mustVerifyJoinTablesInSameDataSource = function mustVerifyJoinTablesInSameDataSource(dataSource, pageContextItemSpec) {
- var itemIds = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : [];
- var moserDataSources = arguments[3];
- //A module can be a package in which case return false (this is the simples case) OR when pageContextItem has no hierarchy context to work on
- var dataSourceType = dataSource.getType && dataSource.getType() || dataSource.getSourceType && dataSource.getSourceType();
- if (dataSourceType === 'package') {
- return false;
- }
- var pageContextColumnIds = pageContextItemSpec && pageContextItemSpec.hierarchies && pageContextItemSpec.hierarchies.map(function (h) {
- return h.hierarchyUniqueName;
- }) || pageContextItemSpec && pageContextItemSpec.getItemIds && pageContextItemSpec.getItemIds();
- if (!_.isArray(pageContextColumnIds) || !pageContextColumnIds.length) {
- return false;
- }
- itemIds.push.apply(itemIds, pageContextColumnIds);
- return DatasourceUtil._shouldVerifyJoin(dataSource, itemIds, moserDataSources);
- };
- DatasourceUtil.haveTableJoinsInSameDataSource = function haveTableJoinsInSameDataSource(module, tableNames, otherTableNames) {
- // TODO Clean internal function names in other classes.
- var tablesHaveJoinRelationship = module.hasJoinedTables ? module.hasJoinedTables.bind(module) : module.tablesHaveJointRelationship.bind(module);
- var result = _.find(otherTableNames, function (otherTableName) {
- return _.find(tableNames, function (tableName) {
- return tablesHaveJoinRelationship(tableName, otherTableName);
- });
- });
- return result ? true : false;
- };
- /**
- * Returns a boolean indicating whether there is a least the same table referenced in both tables
- *
- * @param {array} tableRef1 - table 1 to check
- * @param {array} tableRef2 - the table to check against tableRef1
- *
- * @return {boolean} return true if there is at least one table name matched in both tables, else return false
- */
- DatasourceUtil.haveATableReference = function haveATableReference() {
- var tableRef1 = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : [];
- var tableRef2 = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : [];
- var exactMatch = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : false;
- if (exactMatch && tableRef1.length !== tableRef2.length || tableRef1.length === 0 && tableRef2.length === 0) {
- return false;
- }
- return _.find(tableRef1, function (ref1) {
- return tableRef2.indexOf(ref1) !== -1;
- }) ? true : false;
- };
- /**
- * Dynamically calculates and returns the list of table references for the specified page context entry
- *
- * @param {object} module - the module to retrieve the table names
- * @param {object} pageContextEntry - the page context entry
- *
- * @return {array} List of retrieved table names
- */
- /**
- * Determine whether the slot and dataItem are ordinal and attribute
- *
- * @param {object} slot - The slot item that the function will compare
- * @param {object} dataItem - The dataItem that the function will compare to the slot
- *
- * @return {boolean} A boolean to represent whether or not it is Ordinal vs. Attribute
- **/
- /**
- * Process and return a merged filter page context
- *
- * @param {array} netFilterPageContext - array filter net page context
- * @param {array} synchronizedFilters - array of synchronized filters
- *
- * @return {array} merged synchronized and filter net page context array
- */
- DatasourceUtil.mergeSynchronizePageContextFilter = function mergeSynchronizePageContextFilter(netFilterPageContext, synchronizedFilters) {
- if (!synchronizedFilters || synchronizedFilters.length === 0) {
- return netFilterPageContext;
- }
- var hasFilterByName = function hasFilterByName(filtersToCheck, filterName) {
- var exist = _.find(filtersToCheck, function (filter) {
- return filter.getItemName().toLowerCase() === filterName;
- });
- return exist ? true : false;
- };
- //Populate this vis Filters
- var thisVisFilters = {};
- var getFiltersByScope = function getFiltersByScope(scope) {
- var array = thisVisFilters[scope] = thisVisFilters[scope] || [];
- return array;
- };
- netFilterPageContext.forEach(function (entry) {
- var filters = getFiltersByScope(entry.getScope());
- filters.push(entry);
- });
- //Process synch local filters first because they have precedence over global filters
- var localSynchFilters = synchronizedFilters.filter(function (entry) {
- return entry.scope !== 'global';
- });
- localSynchFilters.forEach(function (entry) {
- var nameToCheck = entry.filterName.toLowerCase();
- var thisTableFilters = getFiltersByScope(entry.scope);
- if (!hasFilterByName(thisTableFilters, nameToCheck)) {
- thisTableFilters.push(entry.getAPI());
- }
- //Remove the same one in the global if it exists since the thisTab one takes precedence since these ones may have been already defined in this vis so remove them
- thisVisFilters.global = _.filter(thisVisFilters.global, function (filter) {
- return filter.getItemName().toLowerCase() !== nameToCheck;
- });
- });
- //Now process synch global filters
- var globalSynchFilters = synchronizedFilters.filter(function (entry) {
- return entry.scope === 'global';
- });
- globalSynchFilters.forEach(function (entry) {
- var nameToCheck = entry.filterName.toLowerCase();
- var toAdd = true;
- //Loop through set of thisTab filters and only add the global filter if it is not defined in the thisTab scope
- for (var property in thisVisFilters) {
- if (property !== 'global' && hasFilterByName(thisVisFilters[property], nameToCheck)) {
- toAdd = false;
- break;
- }
- }
- if (toAdd) {
- var globalFilters = getFiltersByScope('global');
- globalFilters.push(entry.getAPI());
- }
- });
- //Now concat all results and return as a single array
- var result = void 0;
- for (var prop in thisVisFilters) {
- if (thisVisFilters[prop] && thisVisFilters[prop].length > 0) {
- if (!result) {
- result = thisVisFilters[prop];
- } else {
- result = result.concat(thisVisFilters[prop]);
- }
- }
- }
- return result || [];
- };
- DatasourceUtil.metadataColumnSupportsFiltering = function metadataColumnSupportsFiltering(column) {
- if (!column) {
- return false;
- }
- // getAggregateMode is from the old object MetadaColumn
- // getAggregationMode is the new API function
- // the column passed in can be either the old MetadaColumn or the new API Column
- var getAggregationMode = (column.getAggregateMode || column.getAggregationMode).bind(column);
- return !(column.getType() === 'fact' && (getAggregationMode() === 'static' || column.getDefaultAggregation() === 'calculated'));
- };
- return DatasourceUtil;
- }(), _class.getPageContextItemTableRef = function (dataSource, pageContextEntry) {
- var tableRef = [];
- var itemIds = pageContextEntry.getItemIds ? pageContextEntry.getItemIds() : _.pluck(pageContextEntry.hierarchies, 'hierarchyUniqueName');
- itemIds.forEach(function (itemId) {
- var column = dataSource.getMetadataColumn(itemId);
- if (column) {
- var name = column.getTableName();
- if (tableRef.indexOf(name) === -1) {
- tableRef.push(name);
- }
- }
- });
- return tableRef;
- }, _class.isOrdinalAttribute = function (slot, dataItem) {
- var slotType = slot.getDefinition().getType();
- var dataType = dataItem.getMetadataColumn().getType();
- return slotType === 'ordinal' && dataType === 'attribute';
- }, _temp);
- return DatasourceUtil;
- });
- //# sourceMappingURL=DatasourceUtil.js.map
|