1fb726d48Sopenharmony_ci/* 2fb726d48Sopenharmony_ci * Copyright (C) 2022 Huawei Device Co., Ltd. 3fb726d48Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License"); 4fb726d48Sopenharmony_ci * you may not use this file except in compliance with the License. 5fb726d48Sopenharmony_ci * You may obtain a copy of the License at 6fb726d48Sopenharmony_ci * 7fb726d48Sopenharmony_ci * http://www.apache.org/licenses/LICENSE-2.0 8fb726d48Sopenharmony_ci * 9fb726d48Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software 10fb726d48Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS, 11fb726d48Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12fb726d48Sopenharmony_ci * See the License for the specific language governing permissions and 13fb726d48Sopenharmony_ci * limitations under the License. 14fb726d48Sopenharmony_ci */ 15fb726d48Sopenharmony_ci 16fb726d48Sopenharmony_ciexport class JSONToCSV { 17fb726d48Sopenharmony_ci static setCsvData(obj: unknown): void { 18fb726d48Sopenharmony_ci // @ts-ignore 19fb726d48Sopenharmony_ci let data = obj.data; 20fb726d48Sopenharmony_ci // @ts-ignore 21fb726d48Sopenharmony_ci let isShowLabel = typeof obj.showLabel === 'undefined' ? true : obj.showLabel; 22fb726d48Sopenharmony_ci // @ts-ignore 23fb726d48Sopenharmony_ci let fileName = (obj.fileName || 'UserExport') + '.csv'; 24fb726d48Sopenharmony_ci // @ts-ignore 25fb726d48Sopenharmony_ci let columns = obj.columns || { 26fb726d48Sopenharmony_ci title: [], 27fb726d48Sopenharmony_ci key: [], 28fb726d48Sopenharmony_ci formatter: undefined, 29fb726d48Sopenharmony_ci }; 30fb726d48Sopenharmony_ci let showLabel = typeof isShowLabel === 'undefined' ? true : isShowLabel; 31fb726d48Sopenharmony_ci let row = ''; 32fb726d48Sopenharmony_ci let csv = ''; 33fb726d48Sopenharmony_ci let key: string; 34fb726d48Sopenharmony_ci // 如果要现实表头文字 35fb726d48Sopenharmony_ci if (showLabel) { 36fb726d48Sopenharmony_ci // 如果有传入自定义的表头文字 37fb726d48Sopenharmony_ci if (columns.title.length) { 38fb726d48Sopenharmony_ci columns.title.map(function (n: unknown) { 39fb726d48Sopenharmony_ci row += n + ','; 40fb726d48Sopenharmony_ci }); 41fb726d48Sopenharmony_ci } else { 42fb726d48Sopenharmony_ci // 如果没有,就直接取数据第一条的对象的属性 43fb726d48Sopenharmony_ci for (key in data[0]) { 44fb726d48Sopenharmony_ci row += key + ','; 45fb726d48Sopenharmony_ci } 46fb726d48Sopenharmony_ci } 47fb726d48Sopenharmony_ci row = row.slice(0, -1); 48fb726d48Sopenharmony_ci csv += row + '\r\n'; 49fb726d48Sopenharmony_ci } 50fb726d48Sopenharmony_ci // 具体的数据处理 51fb726d48Sopenharmony_ci data.map((n: unknown) => { 52fb726d48Sopenharmony_ci row = ''; 53fb726d48Sopenharmony_ci // 如果存在自定义key值 54fb726d48Sopenharmony_ci if (columns.key.length) { 55fb726d48Sopenharmony_ci row = this.getCsvStr(columns, obj, n, row); 56fb726d48Sopenharmony_ci } else { 57fb726d48Sopenharmony_ci // @ts-ignore 58fb726d48Sopenharmony_ci for (key in n) { 59fb726d48Sopenharmony_ci row += 60fb726d48Sopenharmony_ci // @ts-ignore 61fb726d48Sopenharmony_ci '"' + (typeof columns.formatter === 'function' ? columns.formatter(key, n[key]) || n[key] : n[key]) + '",'; 62fb726d48Sopenharmony_ci } 63fb726d48Sopenharmony_ci } 64fb726d48Sopenharmony_ci row.slice(0, row.length - 1); // 删除最后一个, 65fb726d48Sopenharmony_ci csv += row + '\r\n'; // 添加换行符号 66fb726d48Sopenharmony_ci }); 67fb726d48Sopenharmony_ci if (!csv) { 68fb726d48Sopenharmony_ci return; 69fb726d48Sopenharmony_ci } 70fb726d48Sopenharmony_ci this.saveCsvFile(fileName, csv); 71fb726d48Sopenharmony_ci } 72fb726d48Sopenharmony_ci 73fb726d48Sopenharmony_ci static getCsvStr(columns: unknown, obj: unknown, n: unknown, row: string): string { 74fb726d48Sopenharmony_ci // @ts-ignore 75fb726d48Sopenharmony_ci columns.key.map((m: unknown, idx: number) => { 76fb726d48Sopenharmony_ci let strItem: unknown = ''; 77fb726d48Sopenharmony_ci // @ts-ignore 78fb726d48Sopenharmony_ci if (obj.exportFormatter && obj.exportFormatter.has(m)) { 79fb726d48Sopenharmony_ci // @ts-ignore 80fb726d48Sopenharmony_ci strItem = obj.exportFormatter.get(m)?.(n) || n[m]; 81fb726d48Sopenharmony_ci // @ts-ignore 82fb726d48Sopenharmony_ci } else if (obj.formatter && obj.formatter.has(m)) { 83fb726d48Sopenharmony_ci // @ts-ignore 84fb726d48Sopenharmony_ci strItem = obj.formatter.get(m)?.(n[m]) || n[m]; 85fb726d48Sopenharmony_ci } else { 86fb726d48Sopenharmony_ci // @ts-ignore 87fb726d48Sopenharmony_ci strItem = n[m]; 88fb726d48Sopenharmony_ci } 89fb726d48Sopenharmony_ci if (typeof strItem === 'undefined') { 90fb726d48Sopenharmony_ci strItem = ''; 91fb726d48Sopenharmony_ci } else if (typeof strItem === 'object') { 92fb726d48Sopenharmony_ci strItem = JSON.stringify(strItem); 93fb726d48Sopenharmony_ci // @ts-ignore 94fb726d48Sopenharmony_ci strItem = strItem.replaceAll('"', ''); 95fb726d48Sopenharmony_ci } 96fb726d48Sopenharmony_ci // @ts-ignore 97fb726d48Sopenharmony_ci if (idx === 0 && typeof n.depthCSV !== 'undefined') { 98fb726d48Sopenharmony_ci row += 99fb726d48Sopenharmony_ci '"' + 100fb726d48Sopenharmony_ci // @ts-ignore 101fb726d48Sopenharmony_ci this.treeDepth(n.depthCSV) + 102fb726d48Sopenharmony_ci // @ts-ignore 103fb726d48Sopenharmony_ci (typeof columns.formatter === 'function' ? columns.formatter(m, n[m]) || n[m] : strItem) + 104fb726d48Sopenharmony_ci '",'; 105fb726d48Sopenharmony_ci } else { 106fb726d48Sopenharmony_ci // @ts-ignore 107fb726d48Sopenharmony_ci row += '"' + (typeof columns.formatter === 'function' ? columns.formatter(m, n[m]) || n[m] : strItem) + '",'; 108fb726d48Sopenharmony_ci } 109fb726d48Sopenharmony_ci }); 110fb726d48Sopenharmony_ci return row; 111fb726d48Sopenharmony_ci } 112fb726d48Sopenharmony_ci 113fb726d48Sopenharmony_ci static saveCsvFile(fileName: unknown, csvData: unknown): void { 114fb726d48Sopenharmony_ci let alink: unknown = document.createElement('a'); 115fb726d48Sopenharmony_ci // @ts-ignore 116fb726d48Sopenharmony_ci alink.id = 'csvDownloadLink'; 117fb726d48Sopenharmony_ci // @ts-ignore 118fb726d48Sopenharmony_ci alink.href = this.getDownloadUrl(csvData); 119fb726d48Sopenharmony_ci // @ts-ignore 120fb726d48Sopenharmony_ci document.body.appendChild(alink); 121fb726d48Sopenharmony_ci let linkDom: unknown = document.getElementById('csvDownloadLink'); 122fb726d48Sopenharmony_ci // @ts-ignore 123fb726d48Sopenharmony_ci linkDom.setAttribute('download', fileName); 124fb726d48Sopenharmony_ci // @ts-ignore 125fb726d48Sopenharmony_ci linkDom.click(); 126fb726d48Sopenharmony_ci // @ts-ignore 127fb726d48Sopenharmony_ci document.body.removeChild(linkDom); 128fb726d48Sopenharmony_ci // @ts-ignore 129fb726d48Sopenharmony_ci 130fb726d48Sopenharmony_ci } 131fb726d48Sopenharmony_ci 132fb726d48Sopenharmony_ci static getDownloadUrl(csvData: unknown): string | undefined { 133fb726d48Sopenharmony_ci let result; 134fb726d48Sopenharmony_ci // @ts-ignore 135fb726d48Sopenharmony_ci if (window.Blob && window.URL && (window.URL as unknown).createObjectURL) { 136fb726d48Sopenharmony_ci result = URL.createObjectURL( 137fb726d48Sopenharmony_ci new Blob(['\uFEFF' + csvData], { 138fb726d48Sopenharmony_ci type: 'text/csv', 139fb726d48Sopenharmony_ci }) 140fb726d48Sopenharmony_ci ); 141fb726d48Sopenharmony_ci } 142fb726d48Sopenharmony_ci return result; 143fb726d48Sopenharmony_ci } 144fb726d48Sopenharmony_ci 145fb726d48Sopenharmony_ci static treeDepth(depth: number): string { 146fb726d48Sopenharmony_ci let str = ''; 147fb726d48Sopenharmony_ci for (let i = 0; i < depth; i++) { 148fb726d48Sopenharmony_ci str += ' '; 149fb726d48Sopenharmony_ci } 150fb726d48Sopenharmony_ci return str; 151fb726d48Sopenharmony_ci } 152fb726d48Sopenharmony_ci 153fb726d48Sopenharmony_ci static treeToArr(data: unknown): unknown[] { 154fb726d48Sopenharmony_ci const result: Array<unknown> = []; 155fb726d48Sopenharmony_ci // @ts-ignore 156fb726d48Sopenharmony_ci data.forEach((item: unknown) => { 157fb726d48Sopenharmony_ci let depthCSV = 0; 158fb726d48Sopenharmony_ci const loop = (data: unknown, depth: unknown): void => { 159fb726d48Sopenharmony_ci // @ts-ignore 160fb726d48Sopenharmony_ci result.push({ depthCSV: depth, ...data }); 161fb726d48Sopenharmony_ci // @ts-ignore 162fb726d48Sopenharmony_ci let child = data.children; 163fb726d48Sopenharmony_ci if (child) { 164fb726d48Sopenharmony_ci for (let i = 0; i < child.length; i++) { 165fb726d48Sopenharmony_ci // @ts-ignore 166fb726d48Sopenharmony_ci loop(child[i], depth + 1); 167fb726d48Sopenharmony_ci } 168fb726d48Sopenharmony_ci } 169fb726d48Sopenharmony_ci }; 170fb726d48Sopenharmony_ci loop(item, depthCSV); 171fb726d48Sopenharmony_ci }); 172fb726d48Sopenharmony_ci return result; 173fb726d48Sopenharmony_ci } 174fb726d48Sopenharmony_ci 175fb726d48Sopenharmony_ci static columnsData(columns: Array<unknown>): { 176fb726d48Sopenharmony_ci titleList: unknown[]; 177fb726d48Sopenharmony_ci ketList: unknown[]; 178fb726d48Sopenharmony_ci } { 179fb726d48Sopenharmony_ci let titleList: Array<unknown> = []; 180fb726d48Sopenharmony_ci let ketList: Array<unknown> = []; 181fb726d48Sopenharmony_ci columns.forEach((column) => { 182fb726d48Sopenharmony_ci // @ts-ignore 183fb726d48Sopenharmony_ci let dataIndex = column.getAttribute('data-index'); 184fb726d48Sopenharmony_ci // @ts-ignore 185fb726d48Sopenharmony_ci let columnName = column.getAttribute('title'); 186fb726d48Sopenharmony_ci if (columnName === '') { 187fb726d48Sopenharmony_ci columnName = dataIndex === 'busyTimeStr' ? 'GetBusyTime(ms)' : dataIndex; 188fb726d48Sopenharmony_ci } 189fb726d48Sopenharmony_ci if (columnName !== ' ') { 190fb726d48Sopenharmony_ci titleList.push(columnName); 191fb726d48Sopenharmony_ci ketList.push(dataIndex); 192fb726d48Sopenharmony_ci } 193fb726d48Sopenharmony_ci }); 194fb726d48Sopenharmony_ci return { 195fb726d48Sopenharmony_ci titleList: titleList, 196fb726d48Sopenharmony_ci ketList: ketList, 197fb726d48Sopenharmony_ci }; 198fb726d48Sopenharmony_ci } 199fb726d48Sopenharmony_ci 200fb726d48Sopenharmony_ci static async csvExport(dataSource: { 201fb726d48Sopenharmony_ci columns: unknown[]; 202fb726d48Sopenharmony_ci tables: unknown[]; 203fb726d48Sopenharmony_ci fileName: string; 204fb726d48Sopenharmony_ci columnFormatter: Map<string, (value: unknown) => string>; 205fb726d48Sopenharmony_ci exportFormatter: Map<string, (value: unknown) => string>; 206fb726d48Sopenharmony_ci }): Promise<string> { 207fb726d48Sopenharmony_ci return new Promise((resolve) => { 208fb726d48Sopenharmony_ci let data: unknown = this.columnsData(dataSource.columns); 209fb726d48Sopenharmony_ci let columns = { 210fb726d48Sopenharmony_ci // @ts-ignore 211fb726d48Sopenharmony_ci title: data.titleList, 212fb726d48Sopenharmony_ci // @ts-ignore 213fb726d48Sopenharmony_ci key: data.ketList, 214fb726d48Sopenharmony_ci }; 215fb726d48Sopenharmony_ci if (dataSource.tables.length > 0) { 216fb726d48Sopenharmony_ci if (Array.isArray(dataSource.tables[0])) { 217fb726d48Sopenharmony_ci dataSource.tables.forEach((childArr, childIndex) => { 218fb726d48Sopenharmony_ci let resultArr = JSONToCSV.treeToArr(childArr); 219fb726d48Sopenharmony_ci JSONToCSV.setCsvData({ 220fb726d48Sopenharmony_ci data: resultArr, 221fb726d48Sopenharmony_ci fileName: `${dataSource.fileName}_${childIndex}`, 222fb726d48Sopenharmony_ci columns: columns, 223fb726d48Sopenharmony_ci formatter: dataSource.columnFormatter, 224fb726d48Sopenharmony_ci }); 225fb726d48Sopenharmony_ci }); 226fb726d48Sopenharmony_ci } else { 227fb726d48Sopenharmony_ci let resultArr = JSONToCSV.treeToArr(dataSource.tables); 228fb726d48Sopenharmony_ci JSONToCSV.setCsvData({ 229fb726d48Sopenharmony_ci data: resultArr, 230fb726d48Sopenharmony_ci fileName: dataSource.fileName, 231fb726d48Sopenharmony_ci columns: columns, 232fb726d48Sopenharmony_ci formatter: dataSource.columnFormatter, 233fb726d48Sopenharmony_ci exportFormatter: dataSource.exportFormatter, 234fb726d48Sopenharmony_ci }); 235fb726d48Sopenharmony_ci } 236fb726d48Sopenharmony_ci } 237fb726d48Sopenharmony_ci resolve('ok'); 238fb726d48Sopenharmony_ci }); 239fb726d48Sopenharmony_ci } 240fb726d48Sopenharmony_ci} 241