UNPKG

enigma-mixin

Version:

Set of Qlik Sense enigma.js mixin

1,243 lines (1,226 loc) 63.9 kB
/****************************************************************************** Copyright (c) Microsoft Corporation. Permission to use, copy, modify, and/or distribute this software for any purpose with or without fee is hereby granted. THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. ***************************************************************************** */ /* global Reflect, Promise, SuppressedError, Symbol, Iterator */ function __awaiter(thisArg, _arguments, P, generator) { function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); } typeof SuppressedError === "function" ? SuppressedError : function (error, suppressed, message) { var e = new Error(message); return e.name = "SuppressedError", e.error = error, e.suppressed = suppressed, e; }; function mVariableGetAll(showConfig, showReserved) { return __awaiter(this, void 0, void 0, function* () { const _this = this; const objProp = { qInfo: { qType: "VariableList", }, qVariableListDef: { qData: {}, qShowConfig: false, qShowReserved: false, qType: "variable", }, }; if (showConfig) objProp.qShowConfig = showConfig; if (showReserved) objProp.qShowReserved = showReserved; const sessionObj = yield _this.createSessionObject(objProp); const layout = (yield sessionObj.getLayout()); yield _this.destroySessionObject(sessionObj.id); return layout.qVariableList .qItems; }); } function mVariableUpdateById(id, name, definition, comment) { return __awaiter(this, void 0, void 0, function* () { const _this = this; if (!id) throw new Error(`mVariableUpdateById: "id" parameter is required`); const variable = yield _this.getVariableById(id); const variableProps = yield variable.getProperties(); if (name) variableProps.qName = name; if (definition) variableProps.qDefinition = definition; if (comment) variableProps.qComment = comment; yield variable.setProperties(variableProps); const newProps = yield variable.getProperties(); return newProps; }); } function mVariableUpdateByName(name, newName, definition, comment) { return __awaiter(this, void 0, void 0, function* () { const _this = this; if (!name) throw new Error(`mVariableUpdateByName: "name" parameter is required`); const variable = yield _this.getVariableByName(name); const variableProps = yield variable.getProperties(); if (newName) variableProps.qName = newName; if (definition) variableProps.qDefinition = definition; if (comment) variableProps.qComment = comment; yield variable.setProperties(variableProps); const newProps = yield variable.getProperties(); return newProps; }); } function mVariableCreate(name, definition, comment) { return __awaiter(this, void 0, void 0, function* () { const _this = this; if (!name) throw new Error(`mVariableCreate: "name" parameter is required`); const varProps = { qInfo: { qType: "variable", }, qName: name, qDefinition: definition ? definition : "", qComment: comment ? comment : "", qIncludeInBookmark: false, }; const created = yield _this.createVariableEx(varProps); const variableInst = yield _this.getVariableById(created.id); const props = yield variableInst.getProperties(); return props; }); } function mGetTablesAndFields() { return __awaiter(this, void 0, void 0, function* () { const _this = this; const tables = yield _this.getTablesAndKeys({}, {}, 0, true, false); return tables.qtr .map(function (t) { return t.qFields.map(function (f) { return { table: t.qName, field: f.qName }; }); }) .flat(); }); } function mGetTables() { return __awaiter(this, void 0, void 0, function* () { const _this = this; const qTables = yield _this.getTablesAndKeys({}, {}, 0, true, false); return qTables.qtr.map((t) => t.qName); }); } function mGetFields() { return __awaiter(this, void 0, void 0, function* () { const _this = this; const qTables = yield _this.getTablesAndKeys({}, {}, 0, true, false); return qTables.qtr .map(function (t) { return t.qFields.map(function (f) { return f.qName; }); }) .flat(); }); } // TODO: option to specify if full data to be extracted (loop though all data pages) function mCreateSessionListbox(fieldName, /** * Additional options */ options) { return __awaiter(this, void 0, void 0, function* () { const _this = this; const dataPageHeight = 10000; const lbDef = { qInfo: { qType: options && options.type ? options.type : "session-listbox", }, qListObjectDef: { qStateName: options && options.state ? options.state : "$", qDef: { qFieldDefs: [fieldName], qSortCriterias: [ { qSortByState: 1, qExpression: {}, }, ], }, qInitialDataFetch: [ { qTop: 0, qLeft: 0, qHeight: dataPageHeight, qWidth: 1, }, ], }, }; const obj = yield _this.createSessionObject(lbDef); const [props, layout] = yield Promise.all([ (yield obj.getProperties()), (yield obj.getLayout()), ]); if (options && options.getAllData) { // calculate the total possible data pages const dataPages = Math.ceil(layout.qListObject.qDimensionInfo.qCardinal / dataPageHeight); // if more than 1 then extract all (the first page is already extracted with the initial load) if (dataPages > 1) { // generate index for all data pages const pages = Array.from({ length: dataPages - 1 }, (_, i) => i + 1); yield Promise.all(pages.map((i) => __awaiter(this, void 0, void 0, function* () { const pageData = yield obj.getListObjectData("/qListObjectDef", [ { qTop: i * dataPageHeight, qLeft: 0, qHeight: dataPageHeight, qWidth: 0, }, ]); // push the result to the layout object layout.qListObject.qDataPages.push(pageData[0]); }))); } } if (options && options.destroyOnComplete == true) yield _this.destroySessionObject(obj.id); // call this function to receive all the data in flat format // flat the qMatrix of each qDataPage const flattenData = () => layout.qListObject.qDataPages .map((dp) => dp.qMatrix) .flat(Infinity); return { obj, layout, props, flattenData, }; }); } function mGetSyntheticTables() { return __awaiter(this, void 0, void 0, function* () { const _this = this; const tables = yield _this.getTablesAndKeys({}, {}, 0, true, false); return tables.qtr.filter((t) => t.qIsSynthetic && t.qIsSynthetic == true); }); } function mGetAlwaysOneSelectedFields() { return __awaiter(this, void 0, void 0, function* () { const _this = this; const fields = yield _this.mGetFields(); const alwaysOneSelectedFields = yield Promise.all(fields.map((field) => { return _this .getField(field) .then((f) => f.getNxProperties()) .then((p) => { if (p.hasOwnProperty("qOneAndOnlyOne") && p.qOneAndOnlyOne == true) { return field; } else { return undefined; } }); })).then((fields) => fields.filter((f) => f != undefined)); return alwaysOneSelectedFields; }); } // Core const banditype = (cast) => { cast.map = (extra) => banditype((raw) => extra(cast(raw))); cast.or = (extra) => banditype((raw) => { try { return cast(raw); } catch (err) { return extra(raw); } }); return cast; }; // Error helper const fail = () => "bad banditype"(); const like = ((tag) => banditype((raw) => (typeof raw === typeof tag ? raw : fail()))); const string = () => like(""); const number = () => like(0); const boolean = () => like(true); // Classes const instance = (proto) => banditype((raw) => (raw instanceof proto ? raw : fail())); // arrays const array = (castItem) => instance(Array).map((arr) => arr.map(castItem)); function validateSelectInFieldBySearch(args) { try { string()(args[0]); } catch (e) { throw new Error(`mSelectInField: "fieldName" parameter is required and it must be a string`); } try { string()(args[1]); } catch (e) { throw new Error(`mSelectInField: "values" parameter is required and it must be a string`); } // set "false" as default value for selection toggle const definedToggle = boolean().or(() => false); const defaultedToggle = definedToggle(args[2]); // set "$" as default state is no state or wrong value type is provided const definedState = string().or(() => "$"); const defaultedState = definedState(args[3]); return { defaultedState, defaultedToggle }; } function validateSelectInField(args) { try { string()(args[0]); } catch (e) { throw new Error(`mSelectInField: "fieldName" parameter is required and it must be a string`); } try { array(string().or(number()))(args[1]); } catch (e) { throw new Error(`mSelectInField: "values" parameter is required and it must be an array of strings and/or numbers`); } // set "false" as default value for selection toggle const definedToggle = boolean().or(() => false); const defaultedToggle = definedToggle(args[2]); // set "$" as default state is no state or wrong value type is provided const definedState = string().or(() => "$"); const defaultedState = definedState(args[3]); return { defaultedState, defaultedToggle }; } function iGetSelectionsNative(qDoc) { return __awaiter(this, void 0, void 0, function* () { const lbDef = { qInfo: { qId: "", qType: "CurrentSelection", }, qSelectionObjectDef: {}, }; const sessionObj = yield qDoc.createSessionObject(lbDef); const selections = yield sessionObj.getLayout(); yield qDoc.destroySessionObject(sessionObj.id); return selections; }); } function mSelectionsAll() { return __awaiter(this, void 0, void 0, function* () { const _this = this; const selections = yield iGetSelectionsNative(_this); return selections.qSelectionObject; }); } function mSelectionsFields() { return __awaiter(this, void 0, void 0, function* () { const _this = this; const selections = yield iGetSelectionsNative(_this); const fieldsSelected = selections.qSelectionObject.qSelections.map(function (s) { return s.qField; }); return fieldsSelected; }); } function mSelectionsSimple() { return __awaiter(this, void 0, void 0, function* () { const _this = this; const selections = yield iGetSelectionsNative(_this); return selections.qSelectionObject.qSelections.map(function (s) { const values = s.qSelectedFieldSelectionInfo.map(function (f) { return f.qName; }); return { field: s.qField, values }; }); }); } function mSelectionsSimpleGrouped() { return __awaiter(this, void 0, void 0, function* () { const _this = this; const selections = yield iGetSelectionsNative(_this); return selections.qSelectionObject.qSelections .map(function (s) { return s.qSelectedFieldSelectionInfo.map(function (f) { return { field: s.qField, value: f.qName }; }); }) .flat(); }); } function mSelectInFieldBySearch(fieldName, searchTerm, toggle, state) { var arguments_1 = arguments; return __awaiter(this, void 0, void 0, function* () { var _a, _b; const _this = this; const { defaultedState, defaultedToggle } = validateSelectInFieldBySearch(arguments_1); let { obj: sessionObj, layout } = yield _this.mCreateSessionListbox(fieldName, { state: defaultedState, }); if ((_b = (_a = layout.qListObject) === null || _a === void 0 ? void 0 : _a.qDimensionInfo.qError) === null || _b === void 0 ? void 0 : _b.qErrorCode) throw new Error(`Field "${fieldName}" do not exists. Error code: ${layout.qListObject.qDimensionInfo.qError.qErrorCode}`); const searchResponse = yield sessionObj.searchListObjectFor("/qListObjectDef", searchTerm); if (!searchResponse) throw new Error(`Error while searching the field "${fieldName}" for "${searchTerm}"`); yield sessionObj.acceptListObjectSearch("/qListObjectDef", defaultedToggle); yield _this.destroySessionObject(sessionObj.id); return searchResponse; }); } function mSelectInField(fieldName, values, toggle, state) { var arguments_2 = arguments; return __awaiter(this, void 0, void 0, function* () { var _a, _b; const _this = this; const { defaultedState, defaultedToggle } = validateSelectInField(arguments_2); const { obj: sessionObj, layout } = yield _this.mCreateSessionListbox(fieldName, { destroyOnComplete: false, getAllData: true, state: defaultedState, }); if ((_b = (_a = layout.qListObject) === null || _a === void 0 ? void 0 : _a.qDimensionInfo.qError) === null || _b === void 0 ? void 0 : _b.qErrorCode) throw new Error(`Field "${fieldName}" do not exists. Error code: ${layout.qListObject.qDimensionInfo.qError.qErrorCode}`); const index = layout.qListObject.qDataPages[0].qMatrix .filter((m) => values.indexOf(m[0].qText) > -1) .map((e) => e[0].qElemNumber); const selection = yield sessionObj.selectListObjectValues("/qListObjectDef", index, defaultedToggle); // async function selectMore() { // // // } function destroy() { return __awaiter(this, void 0, void 0, function* () { yield _this.destroySessionObject(sessionObj.id); }); } return { selection, destroy }; }); } function mExtensionObjectsAll() { return __awaiter(this, void 0, void 0, function* () { const _this = this; const allInfos = yield _this.getAllInfos(); const props = yield _this.getAppProperties(); return yield filterOnlyExtensionObjects(this, props, allInfos); }); } function filterOnlyExtensionObjects(qDoc, props, allObjects) { return __awaiter(this, void 0, void 0, function* () { return yield Promise.all(allObjects.map(function (extObj) { return __awaiter(this, void 0, void 0, function* () { const isReallyExtension = yield realExtensionCheck(qDoc, extObj.qId); if (isReallyExtension.isExtension) { return { appId: qDoc.id, appName: props.qTitle, objId: isReallyExtension.qObjProps.qInfo.qId, objType: isReallyExtension.qObjProps.qInfo.qType, extName: isReallyExtension.qObjProps.extensionMeta.name, extVersion: isReallyExtension.qObjProps.version, extVisible: isReallyExtension.qObjProps.extensionMeta.visible, extIsBundle: !isReallyExtension.qObjProps.extensionMeta.isThirdParty, extIsLibrary: isReallyExtension.qObjProps.extensionMeta.isLibraryItem, qProps: isReallyExtension.qObjProps, }; } }); })).then(function (o) { // make sure we filter out all object which are not // native object but are not extensions as well return o.filter(function (a) { return a != undefined; }); }); }); } const realExtensionCheck = function (qDoc, objId) { return __awaiter(this, void 0, void 0, function* () { const nativeObjectTypes = [ "barchart", "boxplot", "combochart", "distributionplot", "gauge", "histogram", "kpi", "linechart", "piechart", "pivot-table", "scatterplot", "table", "treemap", "extension", "map", "listbox", "filterpane", "title", "paragraph", ]; const qObj = yield qDoc.getObject(objId); const qObjProps = yield qObj.getProperties(); if (!qObjProps.visualization) return { isExtension: false }; const isNative = nativeObjectTypes.indexOf(qObjProps.visualization); return { qObjProps, isExtension: isNative == -1 && qObjProps.extensionMeta ? true : false, }; }); }; function mGetBookmarksMeta(state) { return __awaiter(this, void 0, void 0, function* () { state = state ? state : "$"; const _this = this; const listObj = { qInfo: { qId: "BookmarkList", qType: "BookmarkList", }, qBookmarkListDef: { qType: "bookmark", qData: { // dynamic data stored by the Qlik Sense client title: "/qMetaDef/title", description: "/qMetaDef/description", sheetId: "/sheetId", selectionFields: "/selectionFields", creationDate: "/creationDate", }, }, }; const sessionObject = yield _this.createSessionObject(listObj); const sessionObjectLayout = yield sessionObject.getLayout(); const bookmarks = sessionObjectLayout.qBookmarkList.qItems; yield this.destroySessionObject(sessionObject.id); return yield Promise.all(bookmarks.map((bookmark) => __awaiter(this, void 0, void 0, function* () { return yield getBookmarkMeta(bookmark.qInfo.qId, state, _this); }))); }); } function mGetBookmarkMeta(bookmarkId, state) { return __awaiter(this, void 0, void 0, function* () { if (!bookmarkId) throw new Error(`mGetBookmarkMeta: "bookmarkId" parameter is required`); state = state ? state : "$"; const _this = this; return yield getBookmarkMeta(bookmarkId, state, _this); }); } function mCreateBookmarkFromMeta(bookmarkMeta, title, description) { return __awaiter(this, void 0, void 0, function* () { if (!title) throw new Error(`mCreateBookmarkFromMeta: "title" parameter is required`); const _this = this; return yield createBookmarkFromMeta(_this, bookmarkMeta, title, description ? description : ""); }); } function mGetBookmarkValues(bookmarkId, state) { return __awaiter(this, void 0, void 0, function* () { if (!bookmarkId) throw new Error(`mGetBookmarkValues: "bookmarkId" parameter is required`); state = state ? state : "$"; const _this = this; return yield getBookmarkMeta(bookmarkId, state, _this).then((b) => { return b.setAnalysisDestructed; }); }); } function mCloneBookmark(sourceBookmarkId, title, description, state) { return __awaiter(this, void 0, void 0, function* () { if (!sourceBookmarkId) throw new Error(`mCloneBookmark: "sourceBookmarkId" parameter is required`); if (!title) throw new Error(`mCloneBookmark: "title" parameter is required`); state = state ? state : "$"; const _this = this; const sourceBookmarkMeta = yield getBookmarkMeta(sourceBookmarkId, state, _this); return yield createBookmarkFromMeta(_this, sourceBookmarkMeta, title, description ? description : ""); }); } function getBookmarkMeta(bookmarkId, state, qDoc) { return __awaiter(this, void 0, void 0, function* () { const bookmark = yield qDoc.getBookmark(bookmarkId); const [properties, layout, setAnalysisRaw] = yield Promise.all([ yield bookmark.getProperties(), yield bookmark.getLayout(), yield qDoc.getSetAnalysis(state, bookmarkId), ]); const setAnalysisDestructed = destructSetAnalysis(setAnalysisRaw); return { properties, layout, setAnalysisRaw, setAnalysisDestructed, }; }); } function createBookmarkFromMeta(qApp, bookmarkMeta, title, description) { return __awaiter(this, void 0, void 0, function* () { yield qApp.clearAll(true); const makeSelections = yield Promise.all(bookmarkMeta.setAnalysisDestructed.map((s) => __awaiter(this, void 0, void 0, function* () { if (s.type == "list") return yield selectListValues(qApp, s); if (s.type == "expression") return yield selectExpressionValues(qApp, s); }))); if (!makeSelections.every((v) => v === true)) { throw new Error(`Failed to make selection`); } const bookmarkProps = { qInfo: { qType: "bookmark", }, qMetaDef: { title: title, description: description, }, }; const newBookmark = yield qApp.createBookmark(bookmarkProps); const newBookmarkProps = yield newBookmark.getProperties(); return newBookmarkProps.qInfo.qId; }); } function destructSetAnalysis(setAnalysisRaw) { // remove "<" and ">" from the start and the end of the string setAnalysisRaw = /^\<(.*)(.*>)/g.exec(setAnalysisRaw)[1]; // split by "}," but keeping the separator in the result string const regexSplit = /(?<=\},)/; return setAnalysisRaw.split(regexSplit).map((s) => { // remove the "," character from the end (if exists) s = s.replace(/,\s*$/, ""); // get the value between { and } const regexValues = /\{(.*?)\}/; let valueRaw = ""; try { valueRaw = `${regexValues.exec(s)[0]}`; } catch (e) { } let type = ""; let values; // option 1 (general case): if the value is expression (starts with `"` and ends with double quote) const regexExpression = /\"(.*?)\"/; // option 2: if the value is expression (starts with `"=` and ends with double quote) const regexExpression1 = /\"=(.*?)\"/; // if the value is expression if (regexExpression.test(valueRaw)) { type = "expression"; //if starts with `"=` add "=" after the regex // else keep it as it is if (regexExpression1.test(valueRaw)) { values = `=${regexExpression1.exec(valueRaw)[1]}`; } else { values = `${regexExpression.exec(valueRaw)[1]}`; } } // if the value is list of values if (!regexExpression.test(valueRaw)) { type = "list"; let temp = valueRaw.replace(/','/g, '","'); temp = `["${temp.substring(1, temp.length - 1)}"]`; let rawValues = JSON.parse(temp); // determine the value based on the type - string or number // fields are different based on the value type values = rawValues.map((v) => { if (typeof v == "number") return { qIsNumeric: true, qNumber: v, }; if (typeof v == "string") return { qIsNumeric: false, qText: v, }; }); } // extract the field from the expression // first string before ={ let regexField = /(.*?)\={/; let field = regexField.exec(s)[1]; return { field, values, type, }; }); } function selectListValues(qApp, s) { return __awaiter(this, void 0, void 0, function* () { const qField = yield qApp.getField(s.field); return yield qField.selectValues(s.values); }); } function selectExpressionValues(qApp, s) { return __awaiter(this, void 0, void 0, function* () { const listObjectDef = { qInfo: { qType: "bookmark-creation-temp", }, qListObjectDef: { qDef: { qFieldDefs: [s.field], }, }, }; const listObject = yield qApp.createSessionObject(listObjectDef); yield listObject.searchListObjectFor("/qListObjectDef", s.values); const makeSelection = yield listObject.acceptListObjectSearch("/qListObjectDef", false); yield qApp.destroySessionObject(listObject.id); return typeof makeSelection === "object" && Object.keys(makeSelection).length === 0 ? true : false; }); } function mGetDefaultBookmarkId() { return __awaiter(this, void 0, void 0, function* () { const _this = this; const propsObj = { qInfo: { qId: "AppPropsList", qType: "AppPropsList", }, qAppObjectListDef: { qType: "appprops", qData: { sheetTitleBgColor: "/sheetTitleBgColor", sheetTitleGradientColor: "/sheetTitleGradientColor", sheetTitleColor: "/sheetTitleColor", sheetLogoThumbnail: "/sheetLogoThumbnail", sheetLogoPosition: "/sheetLogoPosition", rtl: "/rtl", theme: "/theme", disableCellNavMenu: "/disableCellNavMenu", disableCellContextMenu: "/disableCellContextMenu", chartAnimations: "/chartAnimations", }, }, }; const propsListObject = yield _this.createSessionObject(propsObj); const propsListLayout = yield propsListObject.getLayout(); // no default bookmark (or even appprops in that matter) if (propsListLayout.qAppObjectList.qItems.length == 0) { yield _this.destroySessionObject(propsListObject.id); return ""; } const propsObjectId = propsListLayout.qAppObjectList.qItems.filter((i) => i.qInfo.qType == "appprops")[0].qInfo.qId; yield _this.destroySessionObject(propsListObject.id); const propsObject = yield _this.getObject(propsObjectId); const defaultBookmarkId = yield propsObject .getLayout() .then((l) => l.defaultBookmarkId); return defaultBookmarkId; }); } function mEmptyApp(keepOneSelected) { return __awaiter(this, void 0, void 0, function* () { const _this = this; const currentScript = yield _this.getScript(); if (keepOneSelected == undefined || keepOneSelected == false) { const replaceAndReload = yield _this .setScript("exit script;") .then(() => _this.doReload()) .then(() => _this.setScript(currentScript)) .then(() => _this.doSave()); return replaceAndReload; } let newScriptElements = ["Load"]; const alwaysOneSelectedFields = yield _this.mGetAlwaysOneSelectedFields(); if (alwaysOneSelectedFields.length > 0) { alwaysOneSelectedFields.map((field, i) => { let suffix = i == alwaysOneSelectedFields.length - 1 ? "" : ","; newScriptElements.push(`'${new Date()}' as [${field}]${suffix}`); }); newScriptElements.push("Autogenerate(1);"); newScriptElements.push("exit script;"); } else { newScriptElements = ["exit script;"]; } const newScript = newScriptElements.join("\n"); const replaceAndReload = yield _this .setScript(newScript) .then(() => _this.doReload()) .then(() => _this.setScript(currentScript)) .then(() => _this.doSave()); return replaceAndReload; }); } function mGetAllDataMatrix( /*getPivotData?: boolean*/) { return __awaiter(this, void 0, void 0, function* () { const _this = this; const layout = (yield _this.getLayout()); const dataPageSize = Math.floor(1000 / layout.qHyperCube.qSize.qcx); const numberOfPages = Math.ceil(layout.qHyperCube.qSize.qcy / dataPageSize); const data = yield extractData(_this, numberOfPages, dataPageSize, layout.qHyperCube.qSize.qcx); return data; }); } function mGetAllData( /*getPivotData?: boolean*/) { return __awaiter(this, void 0, void 0, function* () { const _this = this; const layout = (yield _this.getLayout()); const dataPageSize = Math.floor(10000 / layout.qHyperCube.qSize.qcx); const numberOfPages = Math.ceil(layout.qHyperCube.qSize.qcy / dataPageSize); const data = yield extractData(_this, numberOfPages, dataPageSize, layout.qHyperCube.qSize.qcx).then((data) => { return data.map((row) => { const d = []; row.map((cell) => { //@ts-ignore if (cell.qNum != "NaN" || cell.qNum == undefined) { d.push(cell.qNum); } else { d.push(cell.qText); } }); return d; }); }); return data; }); } function extractData(genericObject, numberOfPages, dataPageSize, columns) { return __awaiter(this, void 0, void 0, function* () { let data = []; for (let i = 0; i < numberOfPages + 1; i++) { const page = { qTop: dataPageSize * i, qWidth: columns, qLeft: 0, qHeight: dataPageSize, }; const pageData = yield genericObject .getHyperCubeData("/qHyperCubeDef", [page]) .then((data) => data[0].qMatrix); data = [...data, ...pageData]; } return data; }); } function mUnbuild() { return __awaiter(this, arguments, void 0, function* (sections = []) { const _this = this; if (sections.length == 0) { sections = [ "appProperties", "bookmarks", "connections", "dimensions", "measures", "objects", "script", "variables", "tablesAndFields", ]; } const docData = { variables: undefined, script: undefined, appProperties: undefined, connections: undefined, dimensions: undefined, measures: undefined, objects: undefined, bookmarks: undefined, tablesAndFields: undefined, }; const dimensions = []; const measures = []; const objects = []; if (sections.includes("dimensions") || sections.includes("objects") || sections.includes("measures")) { const appAllInfos = yield _this.getAllInfos(); appAllInfos.map(function (item) { if (item.qType == "dimension") dimensions.push(item.qId); if (item.qType == "measure") measures.push(item.qId); if (item.qType != "dimension" && item.qType != "measure" && item.qType.indexOf("snapshot") == -1 && item.qType != "bookmark" && item.qType != "appprops") { objects.push(item.qId); } }); } yield Promise.all(sections.map((section) => { if (section == "appProperties") return unbuildAppProperties(_this).then((props) => (docData.appProperties = props)); if (section == "bookmarks") return unbuildBookmarks(_this).then((b) => (docData.bookmarks = b)); if (section == "connections") return unbuildConnections(_this).then((c) => (docData.connections = c)); if (section == "dimensions") return unbuildDimensions(_this, dimensions).then((c) => (docData.connections = c)); if (section == "measures") return unbuildMeasures(_this, measures).then((c) => (docData.connections = c)); if (section == "objects") { if (objects.length > 0) docData.objects = {}; return unbuildEntities(_this, objects).then((objectsProps) => { objectsProps.map((o) => { const objType = o.qInfo ? o.qInfo.qType : o.qProperty.qInfo.qType; if (!docData.objects[objType]) docData.objects[objType] = []; docData.objects[objType].push(o); }); }); } if (section == "script") return unbuildScript(_this).then((s) => (docData.script = s)); if (section == "variables") return unbuildVariables(_this).then((v) => (docData.variables = v)); if (section == "tablesAndFields") return _this .getTablesAndKeys({}, {}, 0, true, false) .then((tk) => (docData.tablesAndFields = tk)); })); return docData; }); } function unbuildVariables(app) { return __awaiter(this, void 0, void 0, function* () { const objProp = { qInfo: { qType: "VariableList", }, qVariableListDef: { qData: {}, qType: "variable", qShowReserved: false, qShowConfig: false, }, }; const sessionObj = yield app.createSessionObject(objProp); const sessionObjLayout = yield sessionObj.getLayout(); yield app.destroySessionObject(sessionObj.id); return yield Promise.all(sessionObjLayout.qVariableList.qItems.map((variable) => __awaiter(this, void 0, void 0, function* () { const qVariable = yield app.getVariableById(variable.qInfo.qId); return yield qVariable.getProperties(); }))); }); } function unbuildScript(app) { return __awaiter(this, void 0, void 0, function* () { const script = yield app.getScript(); return script; }); } function unbuildAppProperties(app) { return __awaiter(this, void 0, void 0, function* () { const generalProperties = yield app.getAppProperties(); const propsObj = { qInfo: { qId: "AppPropsList", qType: "AppPropsList", }, qAppObjectListDef: { qType: "appprops", }, }; const propsListObject = yield app.createSessionObject(propsObj); const propsListLayout = yield propsListObject.getLayout(); // if no appprops object exists then nothing more to do if (propsListLayout.qAppObjectList.qItems.length == 0) { yield app.destroySessionObject(propsListObject.id); return { generalProperties, appPropsObject: {} }; } const propsObjectId = propsListLayout.qAppObjectList.qItems.filter((i) => i.qInfo.qType == "appprops")[0].qInfo.qId; yield app.destroySessionObject(propsListObject.id); const propsObject = yield app.getObject(propsObjectId); const appPropsObject = yield propsObject.getProperties(); return { generalProperties, appPropsObject }; }); } function unbuildConnections(app) { return __awaiter(this, void 0, void 0, function* () { const appConnections = yield app.getConnections(); return appConnections; }); } function unbuildBookmarks(app) { return __awaiter(this, void 0, void 0, function* () { const listObj = { qInfo: { qId: "BookmarkList", qType: "BookmarkList", }, qBookmarkListDef: { qType: "bookmark", qData: { // dynamic data stored by the Qlik Sense client title: "/qMetaDef/title", description: "/qMetaDef/description", sheetId: "/sheetId", selectionFields: "/selectionFields", creationDate: "/creationDate", }, }, }; const sessionObject = yield app.createSessionObject(listObj); const sessionObjectLayout = yield sessionObject.getLayout(); const bookmarks = sessionObjectLayout.qBookmarkList.qItems; yield app.destroySessionObject(sessionObject.id); const completeBookmarksInfo = yield Promise.all(bookmarks.map((bookmark) => __awaiter(this, void 0, void 0, function* () { return yield getBookmarkMeta(bookmark.qInfo.qId, "$", app); }))); const defaultBookmarkId = yield app.mGetDefaultBookmarkId(); completeBookmarksInfo.map((bookmark) => { if (bookmark.properties.qInfo.qId == defaultBookmarkId) { bookmark["isDefault"] = true; } else { bookmark["isDefault"] = false; } }); return completeBookmarksInfo; }); } function unbuildDimensions(app, dimensions) { return __awaiter(this, void 0, void 0, function* () { yield Promise.all(dimensions.map((dim) => app.getDimension(dim.qId).then((dimObj) => dimObj.getProperties()))); }); } function unbuildMeasures(app, measures) { return __awaiter(this, void 0, void 0, function* () { yield Promise.all(measures.map((m) => app.getMeasure(m.qId).then((mObj) => mObj.getProperties()))); }); } function unbuildEntities(app_1) { return __awaiter(this, arguments, void 0, function* (app, objIds = []) { return Promise.all(objIds.map((objId) => processObject(objId, app))).then((objsData) => objsData.filter((d) => d != undefined)); }); } function processObject(qId, app) { return __awaiter(this, void 0, void 0, function* () { const obj = yield app.getObject(qId); // embeddedsnapshot, snapshot, hiddenbookmark, story --> need to be handled differently const hasParent = yield obj .getParent() .then(() => true) .catch(() => false); const hasChildren = yield obj.getChildInfos(); // parent-less objects - masterobject, sheet, appprops, LoadModel if (hasParent == false) { if (hasChildren.length > 0) { return yield obj.getFullPropertyTree(); } else { return yield obj.getProperties(); } } }); } // TODO: ... // * appProperties - where the icon? // * appProperties - theme is different from the source app? // * connections - created, but why not visible? // * purge - option to remove everything from the app before // build is started function mBuild(arg) { return __awaiter(this, void 0, void 0, function* () { return Promise.all([ yield processMeasures(arg.measures, this), yield processDimensions(arg.dimensions, this), yield processScript(arg.script, this), yield processAppProperties(arg.appProperties, this), yield processConnections(arg.connections, this), yield processVariables(arg.variables, this), yield processObjects(arg.objects, this), ]) .then(function (d) { return { measures: d[0], dimensions: d[1], script: d[2], appProperties: d[3], connections: d[4], variables: d[5], objects: d[6], }; }) .then((data) => { const notNullKeys = Object.keys(data).filter((k) => data[k] != undefined); return Object.fromEntries(Object.entries(data).filter(([key]) => Array.from(notNullKeys).includes(key))); }); }); } function processMeasures(measures, app) { return __awaiter(this, void 0, void 0, function* () { if (measures && measures.length > 0) { return Promise.all(measures.map(function (measure) { return __awaiter(this, void 0, void 0, function* () { let obj = {}; // the measure do not exists and need to be created try { obj = yield app.getMeasure(measure.qInfo.qId); } catch (e) { } if (!obj.id) { yield app.createMeasure(measure); return { qId: measure.qInfo.qId, status: "Created" }; } // the measure exists and need to be updated yield obj.setProperties(measure); return { qId: measure.qInfo.qId, status: "Updated" }; }); })); } }); } function processDimensions(dimensions, app) { return __awaiter(this, void 0, void 0, function* () { if (dimensions && dimensions.length > 0) { return Promise.all(dimensions.map(function (dimension) { return __awaiter(this, void 0, void 0, function* () { let obj = {}; try { obj = yield app.getDimension(dimension.qInfo.qId); } catch (e) { } // the dimension do not exists and need to be created if (!obj.id) { yield app.createDimension(dimension); return { qId: dimension.qInfo.qId, status: "Created" }; } // the dimension exists and need to be updated yield obj.setProperties(dimension); return { qId: dimension.qInfo.qId, status: "Updated" }; }); })); } }); } function processScript(script, app) { return __awaiter(this, void 0, void 0, function* () { if (script) { yield app.setScript(script); return { status: "Set" }; } }); } function processAppProperties(appProperties, app) { return __awaiter(this, void 0, void 0, function* () { if (appProperties) { yield app.setAppProperties(appProperties); return { status: "Set" }; } }); } function processConnections(connections, app) { return __awaiter(this, void 0, void 0, function* () { if (connections && connections.length > 0) { const appConnections = yield app.getConnections(); return Promise.all(connections.map(function (connection) { return __awaiter(this, void 0, void 0, function* () { const conn = appConnections.find((o) => o.qName === connection.qName); if (!conn) { yield app.createConnection(connection); return { qId: connection.qName, status: "Created" }; } yield app.modifyConnection(conn.qId, connection, true); return { qId: connection.qName, status: "Updated" }; }); })); } }); } function processVariables(variables, app) { return __awaiter(this, void 0, void 0, function* () { if (variables && variables.length > 0) { return Promise.all(variables.map(function (variable) { return __awaiter(this, void 0, void 0, function* () { let qVar; try { qVar = yield app.getVariableByName(variable.qName); } catch (e) { } if (!qVar || !qVar.id) { yield app.createVariableEx(variable); return { qId: variable.qName, status: "Created" }; } yield qVar.setProperties(variable); return { qId: variable.qName, status: "Updated" }; }); })); } }); } function processObjects(objects, app) { return __awaiter(this, void 0, void 0, function* () { if (objects && objects.length > 0) { return Promise.all(objects.map(function (object) { return __awaiter(this, void 0, void 0, function* () { let objId, objType; let isGenericObject = false; //if the object is GenericObject - the id and the type are in a slightly different path if (!object.qInfo) { isGenericObject = true; objId = object.qProperty.qInfo.qId; objType = object.qProperty.qInfo.qType; } else { objId = object.qInfo.qId; objType = object.qInfo.qType; } let obj; try { obj = yield app.getObject(objId); } catch (e) { } if (obj && obj.id) { // if its GenericObject we have to set the the props using setFullPropertyTree if (isGenericObject) { yield obj.setFullPropertyTree(object); return { qId: objId, status: "Updated" }; } // if not GenericObject then use the "usual" setProperties if (!isGenericObject) { yield obj.setProperties(object); return { qId: objId, status: "Updated" }; } } // same rules are applied when we have to create the object if (!obj || !obj.id) { if (isGenericObject) { const o = yield app.createObject({ qInfo: { qId: `${objId}`, qType: objType, }, }); yield o.setFullPropertyTree(object); return { qId: objId, status: "Created" }; } if (!isGenericObject) { yield app.createObject(object); return { qId: objId, status: "Created" }; } } }); })); } }); } function getDefaultExportFromCjs (x) { return x && x.__e